意外的“瞬态”构造函数修饰符

时间:2013-01-05 10:03:17

标签: java reflection jvm

我在使用反射时发现了一些有趣的东西。我试图检索简单类及其修饰符的构造函数。

public class Test {
    public Test(Object... args) {}
}

以下是检索构造函数修饰符的代码:

Class<?> clazz = Test.class;
Constructor<?>[] ctors = clazz.getDeclaredConstructors();
for (Constructor<?> ctor : ctors) {        
    int mod = ctor.getModifiers();
    /*if not package-private modifier*/
    if(mod!=0) {
        System.out.println( Modifier.toString(mod)));
    }
}

结果是:

    public transient  

如果我传递的构造函数不是变量参数,而只是数组,那就没关系。

public class Test {
    public Test(Object[] args) {}
}

结果是:

    public  

无论构造函数修饰符(public,protected,private)还是参数类型(primitive或reference),都会发生同样的情况。怎么可能,而“transient”对于构造函数来说不是有效的修饰符?

1 个答案:

答案 0 :(得分:17)

访问修饰符在类文件中编码为位掩码。 JVM规范为某些位赋予不同的含义,具体取决于它们是出现在方法修饰符还是字段修饰符中。第7位(0x0080)就是这样一个位。

For methods

ACC_VARARGS    0x0080  Declared with variable number of arguments.

For fields

ACC_TRANSIENT  0x0080  Declared transient; not written or read by a persistent
                       object manager.

由于您正在查看某个方法,因此对此修饰符的正确解释为ACC_VARARGS而不是ACC_TRANSIENT

但是,Modifier类似乎只能处理JVM规范中定义的修饰符子集。因为所需要的只是int,所以它无法区分ACC_VARARGSACC_TRANSIENT