2012-07-08 22 views
0

我看着使用ASM一些Java字节码,并感到非常惊讶,当我看到这几行Java类中的INNERCLASS字段如何使用?

public class C1 { 

    // compiled from: C1.java 
    // access flags 0x9 
    public static INNERCLASS C2$C3 C2 C3 

    //.. 
} 

C1INNERCLASS声明包含在C2类。这是应该如何?如果是这样,为什么它需要,而不是导致多余的冗余?

我使用Eclipse Indigo SR1编译了一个最小的示例,该示例在外部类型的主方法中具有内部类型的局部变量,以表示它的价值。我应该报告一个错误吗?


public class C1 { 
    public static void main(String[] args) throws Exception { 
     C2.C3 c3 = new C2.C3(); 

     ClassReader cr = new ClassReader(C1.class.getName()); 
     cr.accept(new TraceClassVisitor(new PrintWriter(System.out)), 0); 
    } 
} 

public class C2 { 
    public static class C3 {} 
} 
+0

原始Java文件是什么样的?从你的描述来看,这并不是很清楚。不必是完整的代码,但看到重要的部分可能会有所帮助。 – eran 2012-07-08 14:03:09

+0

我将精确的测试代码添加到问题中;它只不过是我说的;) – 2012-07-08 14:16:08

回答

1

Java Virtual Machine Specification

如果一个类或接口C的常量池中包含至少一个CONSTANT_Class_info条目(§4.4.1),其代表一个不是包成员的类或接口,那么ClassFile结构的attributes表中必须只有一个InnerClasses属性C.

即,InnerClasses属性引用在类文件中引用的所有内部类(“类或接口不是一个包的部件”),即使它们是不包含在所述类的成员在类文件中。另一起案件(可能被要求缺乏具体术语外班)在一份报告中被明确地叫了一声:

此外,每嵌套类和嵌套接口的constant_pool表必须是指其封闭类,因此,每个嵌套类和嵌套接口都会为每个封闭类以及每个嵌套类和接口拥有InnerClasses信息。

至于为什么需要这些外部引用,我不能完全肯定,但要注意的是,在Java 1.1中加入内部类后的类文件格式主要是冷冻的,所以关于内部类的信息是不像超类,接口,字段和方法一样,直接存储在ClassFile结构(类文件的顶层结构)中。还要注意InnerClasses属性是8个字节加上引用的每个内部类的8个字节 - 这几乎不是过多的冗余。

相关问题