3

使用最新的 JAXB (Metro) 并使用 XJC 生成 Java....

想要(正如其他用户所问的)生成 java.util.Set 作为表示无界序列的字段的类型。看起来这种类型的字段被 XJC 捕获为 UntypedListField 并且默认行为是生成 java.util.List (仅 getter)。如果我执行类似于 collection-setter-injector 插件的操作并调整字段的类型,例如

 public boolean run(Outline model, Options opt, ErrorHandler errorHandler) {
    for (ClassOutline co : model.getClasses()) {
       FieldOutline[] fo = co.getDeclaredFields();

       for ...
          if ((fo[i] instanceof UntypedListField)) {
            --> DO SOMETHING WITH THIS FIELD
          }
    }
 }

人们如何调整类型,或者构建一个新字段然后在类大纲中声明的字段集中替换它是否更容易?弄乱字段的类型如何影响属性上 get 方法的生成?

4

1 回答 1

1

看起来您要使用自己的 XJC 插件。所以这就是你需要做的。用以下内容替换您的--> DO SOMETHING WITH THIS FIELD行。

首先,弄清楚fo[i](我称之为 f)的参数化类型是什么。然后,创建 Set JType。最后将类型设置fsetType

JType inner = ((JClass)f.type()).getTypeParameters().get(0);
JType setType = co.parent().getCodeModel().ref(Set.class).narrow(inner);
f.type(setType);

该方法narrow()用于设置参数化类型。

到目前为止看起来不错,但问题是插件将在 XJC 完成生成类后运行。这意味着吸气剂已经在那里。所以我们需要更换它。

这是replaceGetter()方法

private void replaceGetter(ClassOutline co, JFieldVar f, JType inner) {
    //Create the method name
    String get = "get";
    String name  = f.name().substring(0, 1).toUpperCase() 
            + f.name().substring(1);
    String methodName = get+name;

    //Create HashSet JType
    JType hashSetType = co.parent().getCodeModel().ref(HashSet.class).narrow(inner);

    //Find and remove Old Getter!
    JMethod oldGetter = co.implClass.getMethod(methodName, new JType[0]);
    co.implClass.methods().remove(oldGetter);

    //Create New Getter
    JMethod getter = co.implClass.method(JMod.PUBLIC, f.type(), methodName);

    //Create Getter Body -> {if (f = null) f = new HashSet(); return f;}
    getter.body()._if(JExpr.ref(f.name()).eq(JExpr._null()))._then()
    .assign(f, JExpr._new(hashSetType));

    getter.body()._return(JExpr.ref(f.name()));
}

希望你觉得这很有帮助。

于 2013-09-08T02:02:25.507 回答