From Java Language Specification - 8.5 Element Type Declaration
If a class declares a member type with a specific name, then a declaration of this type is called to hide all available declarations of member types with the same name in superclasses and superinterfaces of the class.
A class inherits from its direct superclass and direct superinterfaces, all types of infrequent members of the superclass and superinterfaces that are available for code in the class, rather than a hidden declaration in the class.
It can be concluded that:
B.Inner hiding A.Inner . B does not inherit A.Inner . A.Inner not a member of (8.2) type B C cannot inherit A.Inner from B C cannot inherit B.Inner from B because it is closed.
Therefore, C not an Inner member type. Assume that there is no other type of Inner in areas of the C environment (external class, compilation unit, package), then the type name Inner cannot be resolved.
javac trying to report a more detailed error, but this is only a guess at your intention. Even the best error message should probably include all of the above explanations.
In the first example of Entry the import statement declares Entry in the entire scope of the compilation unit (that is, in the java file), so Entry allowed to be Map.Entry
IntelliJ 10.5 does not complain about the first example; apparently bug fixed. In the second example, this is still wrong.
There is something funny in private . Why does the specification explicitly exclude private members, while it already requires members to be "accessible"? In fact, B.Inner is available throughout CompileTest (6.6.1), including C C may have doStuff(B.Inner) and it will be compiled.
Probably why IntelliJ screwed up the second example; he believes B.Inner is available for C , so C inherits B.Inner . He did not take into account the proposal for the additional exclusion of private members in inheritance.
This shows two conflicting views on the scope of the private declaration. View # 1 requires the scope to be the immediate spanning class, view # 2 is the class spanning the top level. # 2 less well-known to programmers, they are surprised to learn that C can access B.Inner . # 2 can be justified as follows: all the same, they are all in one file, therefore there is no need for encapsulation, we do not protect anyone by denying access; allowing access in most cases is more convenient.
View # 2 probably also argued that C should inherit B.Inner - what could go wrong? Interestingly, No. 2 wins the general access control rule, but loses the inheritance rule.
The spectrum is really really dirty, fortunately, we usually do not encounter these difficult situations. This is more likely a bug LinkedHashMap and HashMap , which renames the public name for private use.