有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

有没有办法将java arraylist对象复制到codemodel生成的源代码中?

我在使用codemodel的代码生成类中有一个填充的arraylist(非codemodel),我想在生成的代码中使用它。有什么办法吗?它有点“跨越世界”,因为生成的代码不引用或依赖生成它的代码,但是我仍然希望使用arraylist的值,而不必在逐个值的遍历中手动复制它。。。一定有办法做到这一点,就像字符串、数字等

我的示例代码如下:

private JMethod makeHeadersWrapper( String endPointName, ArrayList<BasicNameValuePair> headersList )
{

    JMethod wrapperMethod = definedClass.method( JMod.PUBLIC | JMod.STATIC, codeModel.ref( headersList.getClass() ).narrow( BasicNameValuePair.class ), StringUtils.formatName( "make" + endPointName + "Header", false, StringUtils.FormatType.UP_ENGLISH_WORDS ) );

    JVar headersListVar = wrapperMethod.body().decl( wrapperMethod.type(), "headersList", {X} ) );
    wrapperMethod.body()._return( headersListVar );

    return wrapperMethod;

}

正如你们在我的作业声明中看到的,有一个{X}空白字段,这就是我试图弄清楚如何写的。也就是说,{X}应该引用makeHeadersWrapper签名中的'headersList'参数。有没有办法将变量的值引用为{X},并使其成为codemodel JExpr(Session)?请帮我解{X}!:P

衷心感谢, 皮奥特


共 (1) 个答案

  1. # 1 楼答案

    基本上我不认为JExpression支持列表。它确实有一个JArray,但仍然需要在headersList上迭代。直到codemode-2.6,在JExprJExpression中没有迭代列表的方法。所以你无法逃脱迭代部分。因此,标准做法是迭代headersList并添加初始化语句

    比如说,你有一个名值对,比如

    public class BasicNameValuePair {
        private String name;
        private String value;
    
        public BasicNameValuePair(String name, String value) {
            this.name = name;
            this.value = value;
        }
        //getters & setters
    }
    

    就像

    List<BasicNameValuePair> headerList = new ArrayList<BasicNameValuePair>();
    headerList.add(new BasicNameValuePair("1", "1"));
    headerList.add(new BasicNameValuePair("2", "2"));
    headerList.add(new BasicNameValuePair("3", "3"));
    headerList.add(new BasicNameValuePair("4", "4"));
    

    然后你可以生成你的方法体

    private JMethod makeHeadersWrapper( String endPointName, List<BasicNameValuePair> headersList ) {
    
        JClass headerClass = codeModel.ref( headersList.getClass() ).narrow( BasicNameValuePair.class );
        JMethod wrapperMethod = definedClass.method( JMod.PUBLIC | JMod.STATIC, headerClass, ( "make" + endPointName + "Header") );
    
        JVar headersListVar = wrapperMethod.body().decl( wrapperMethod.type(), "headersList", JExpr._new(headerClass) );
        for(BasicNameValuePair nameValuePair : headersList) {
            wrapperMethod.body().add(headersListVar.invoke("add").arg(JExpr._new(nameValuePairClass).arg(nameValuePair.getName()).arg(nameValuePair.getValue())));
        }
        wrapperMethod.body()._return( headersListVar );
    
        return wrapperMethod;
    }
    

    这将生成代码

    public static ArrayList<BasicNameValuePair> makeTestHeader() {
        ArrayList<BasicNameValuePair> headersList = new ArrayList<BasicNameValuePair>();
        headersList.add(new BasicNameValuePair("1", "1"));
        headersList.add(new BasicNameValuePair("2", "2"));
        headersList.add(new BasicNameValuePair("3", "3"));
        headersList.add(new BasicNameValuePair("4", "4"));
        return headersList;
    }
    

    但是ArrayList有一个使用{{ }}的构造函数方法。所以你可以申报

    List<String> lst = new ArrayList<String>(){{ add("1"); add("2"); add("3"); add("4"); }};
    

    而且JExpr有一个direct()方法,我们可以直接传递源代码。使用这两种方法,我们可以生成如下代码。我不推荐这种方法,但它是可能的

    private JMethod makeHeadersWrapper( String endPointName, List<BasicNameValuePair> headersList ) {
        JMethod wrapperMethod = definedClass.method( JMod.PUBLIC | JMod.STATIC, codeModel.ref( headersList.getClass() ).narrow( BasicNameValuePair.class ), ( "make" + endPointName + "Header") );
    
        JVar headersListVar = wrapperMethod.body().decl( wrapperMethod.type(), "headersList", JExpr.direct(generateListConstructor(headersList)) );
        wrapperMethod.body()._return( headersListVar );
    
        return wrapperMethod;
    
    }
    
    private String generateListConstructor(List<BasicNameValuePair> headersList) {
        StringBuilder listEpr = new StringBuilder("new ArrayList<scope.BasicNameValuePair>(){{");
        for(BasicNameValuePair nameValuePair : headersList) {
            listEpr.append("add(new BasicNameValuePair(\"").append(nameValuePair.getName()).append("\", \"").append(nameValuePair.getValue()).append("\")); ");
        }
        return listEpr.append("}}").toString();
    }
    

    这将产生

    public static ArrayList<BasicNameValuePair> makeTestHeader() {
        ArrayList<BasicNameValuePair> headersList = (new ArrayList<scope.BasicNameValuePair>(){{add(new BasicNameValuePair("1", "1")); add(new BasicNameValuePair("2", "2")); add(new BasicNameValuePair("3", "3")); add(new BasicNameValuePair("4", "4")); }});
        return headersList;
    }
    

    这也是一个有效的java代码

    这个答案可能不是你想要的答案,但它可能会给你一个前进的想法。希望这有帮助