无法从静态上下文中引用内部 class,但前提是外部 class 是通用的

Can't reference inner class from a static context, but only if outer class is generic

以下将无法编译:

class Outer<T> {
    class Inner {

    }

    static class Nested {
        Inner inner; // Error: Outer.this cannot be referenced from a static context
    }
}

但是,如果我删除 <T>,它会编译。为什么不一致?

此外,如果我说 Outer.Inner inner; 而不是 Inner inner;,它会编译。同样,为什么不一致?

我预计在所有情况下都会出现错误,或者 none。谁能解释一下这是怎么回事?

class OuterClass {

    ...
    static class StaticNestedClass {
        ...
    }
    class InnerClass {
        ...
    }
}

嵌套的 class 是其封闭 class 的成员。非静态嵌套 classes(内部 classes)可以访问封闭 class 的其他成员,即使它们被声明为私有。静态嵌套 classes 无法访问封闭 class.

的其他成员
Static Nested Classes

与 class 方法和变量一样,静态嵌套 class 与其外部 class 关联。和静态 class 方法一样,静态嵌套 class 不能直接引用其封闭 class 中定义的实例变量或方法:它只能通过对象引用来使用它们。

使用封闭的 class 名称访问静态嵌套 classes:

OuterClass.StaticNestedClass

例如,要为静态嵌套 class 创建对象,请使用以下语法:

OuterClass.StaticNestedClass nestedObject =
 new OuterClass.StaticNestedClass();

有关更多信息,请单击以下内容:

https://docs.oracle.com/javase/tutorial/java/javaOO/nested.html

为什么不一致?

我想说这根本不是自相矛盾。这基本上是对泛型的理解问题。考虑以下代码(您修改的代码):

class Outer<T> {
    class Inner{
        T t;//Added this extra line
    }

    static class Nested {
        Inner inner; 
    }
}

在上面的示例中,与您所写的有些相似,只是我添加了一个类型为 T 的新变量 t,它是 Outer [=47= 的泛型] 在 class Inner 中。现在在上面的示例中不会编译,因为 Inner class 中存在非静态或运行时引用,因此,当您在静态 class 中声明 InnerNested JAVA 编译器不知道 T 的类型,它只在运行时声明,所以你会得到一个错误。但是在您的情况下,您没有做任何类似的事情,但编译器仍然不知道是否存在类似的事情。所以它给出了错误。

现在,在第二种情况下,您已从 Outer 的 class 声明中删除了通用 T。所以不可能在 Inner class 中声明变量 t 所以没有错误。

在第三种情况下,您为变量类型 inner 声明了 Outer.Inner 并且编译成功。这里编译器将 Outer 视为 RAW TYPE。但是应该避免这种类型的原始类型声明。所以最好写成:

 Outer<?>.Inner inner;

此处Java编译器认为Outer将任何对象作为参数继承Object