Java 静态嵌套类不初始化外部类

Java 静态嵌套类不初始化外部类,java,inner-classes,Java,Inner Classes,当我初始化静态内部类时,我希望外部类也被初始化,并将打印,我也应该看到这一点。但是这并没有发生,我只得到类Main作为输出 class AA { static { System.out.println("I should see this as well."); } public static class BB { BB() { Object o = Main.class; System

当我初始化静态内部类时,我希望外部类也被初始化,并将打印
,我也应该看到这一点。
但是这并没有发生,我只得到
类Main
作为输出

 class AA {
    static {
        System.out.println("I should see this as well.");
    }

    public static class BB {
        BB() {
            Object o = Main.class; 
            System.out.println(o.toString());
        }
    };
}

public class Test {
    public static void main(String[] args) {
        new AA.BB();
    }
}

有人能帮我解释一下这种行为吗。

问题是:static初始化程序块被延迟执行。意思是:当AA类确实是“必需的”时,该代码第一次被执行。但是AA不需要实例化AA$BB

如果你改变

BB() {
  Object o = Main.class; 
  System.out.println(o.toString());
}
要真正要求加载AA类,请执行以下操作:

BB() {
  Object o = Main.class; 
  System.out.println(o.toString());
  new AA();
}
然后另一个字符串也被打印出来

请记住:只有在源代码中BB才是AA的“内部”。从类加载器的角度来看,AA和BB(不知何故)是两个独立的类,它们来自两个不同的类文件

编辑,给出“如何查看”的问题:

A) 我用Test.class替换Main.class并进行编译,然后在我的文件系统
AA$BB.class AA.class Test.class
中找到


B) 现在,您可以运行
[javap][1]-c“AA$BB.class”
来查看有关该类内容的更多信息

嵌套类会创建一个不同的类。

这里有两个课程:

  • AA级

  • AA$BB.class


使用第二个类不需要加载第一个类,因为第二个类是公共静态类。

静态内部类与其外部类的关系不如非静态类密切。事实上,您可以将静态内部类的外部类视为某种名称空间(或包)。静态嵌套类与其外部类(和其他类)的实例成员进行交互,就像任何其他顶级类一样。实际上,静态嵌套类在行为上是一个顶级类,为了便于打包而嵌套在另一个顶级类中。一旦它们被编译,它们就足够分开,你可以加载一个类而不加载另一个。。。有趣的事。我投赞成票!哇-那么AA和AA.BB实现为不同的类?从没想过!当您说“从类加载器的角度来看,AA和BB(不知何故)是来自两个不同类文件的两个独立类”时,您是对的!-我想用您推荐的任何工具或其他方式检查此行为。@Show Stopper???您的问题包括已经显示此行为的代码!这是你问题的基础,它显示了你的行为!问题中没有内部类。
BB
是静态的。因此,它不是一个内部类。请阅读上的精美手册。“内部类是一个嵌套类,它不是显式或隐式声明为静态的。”@Lew Bloch您向我学到了一些东西。完成:“嵌套类分为两类:静态类和非静态类。声明为静态的嵌套类称为静态嵌套类。非静态嵌套类称为内部类。”。因此我进行了编辑。您没有编辑您的答案以删除对“内部类”的错误引用。