Java反射:按声明顺序获取字段和方法

时间:2011-02-15 08:07:19

标签: java reflection junit

有没有办法按照声明的顺序使用反射来获取类声明的字段(和方法)?根据文档,getFields()getDeclaredFields()等返回的方法和字段的顺序未定义。

使用Java reflection: Is the order of class fields and methods standardized?

中建议的注释,可以指定索引之类的内容

有没有更好的选择,即不必手动指定索引?

现在在你问我需要什么之前:我们有一个方法,它将一个非常大的数据结构作为输入并对其进行冗长的计算。为了创建单元测试,我们创建了一个方法,该方法接受输入对象和输出实例,并创建Java源代码(设置输入,调用计算方法,然后断言正确的结果)作为输出。当字段按声明顺序写入时,此代码更易读。

6 个答案:

答案 0 :(得分:11)

使用jdk 6,反映的字段按其声明顺序显示。在早期的jdk中并非如此。显然有足够的人唠叨。

虽然javadoc不能保证,但我仍然认为这个顺序是合格的,我认为订单也将保留在未来的jdks中。

在您的应用程序中,就像在大多数应用程序中一样,对声明顺序的依赖主要是虚荣 - 如果订单搞砸了,您的应用程序不会失败,它只会变得有点丑陋。

答案 1 :(得分:5)

不,反射不可能。但是,您可以使用ProcessBuilderjavap命令解决此问题:

给出Test.java

public abstract class Test {

    public void method1() {
    }

    public void method2() {
    }

    public static void main(String[] args) {
    }

    public String method3() {
        return "hello";
    }

    abstract void method4();

    final int method5() {
        return 0;
    }
}

命令javap Test打印:

...
public Test();
public void method1();
public void method2();
public static void main(java.lang.String[]);
public java.lang.String method3();
abstract void method4();
final int method5();
...

答案 2 :(得分:4)

我认为这是一个孤立的问题,请看

https://github.com/wmacevoy/kiss/blob/master/src/main/java/kiss/util/Reflect.java

和方法

  

public static Method [] getDeclaredMethodsInOrder(Class clazz)

通过查看类的字节码来获取顺序。如果你只是想使用libray,那就是 kiss.util.Reflect.getDeclaredMethodsInOrder(Test.class)

答案 3 :(得分:2)

如果不修改编译过程,我担心这是不可能的。通常,字段会以任何顺序写入类文件,并且有关声明顺序的信息会丢失。

很可能您可以使用注释处理器在辅助文件中编写订单。

应该很容易。看,例如以interfacegen为例,注释处理器如何工作。您可能希望将信息放在同一个文件中,但这要困难得多。

答案 4 :(得分:1)

您可以考虑将Javadoc与自定义Doclet一起使用,但这需要源可用。

仍无法保证API中的顺序(methodsfields,但我见过的每个javadoc输出都按正确的顺序排列,所以我想doclet会得到它们按照申报顺序。

答案 5 :(得分:0)

您将无法从类文件中获取信息。正如亚当在回答其他问题时所说:

  

返回的数组中的元素没有排序,也没有任何特定的顺序。

“无订单”包括“无申报单”。

我曾经使用Java源文件解析器来获取代码生成器的输入数据。通过这种方式,您将按声明顺序拥有字段和方法。