Win a copy of TensorFlow 2.0 in Action this week in the Artificial Intelligence and Machine Learning forum!
  • Post Reply Bookmark Topic Watch Topic
  • New Topic
programming forums Java Mobile Certification Databases Caching Books Engineering Micro Controllers OS Languages Paradigms IDEs Build Tools Frameworks Application Servers Open Source This Site Careers Other all forums
this forum made possible by our volunteer staff, including ...
Marshals:
  • Campbell Ritchie
  • Liutauras Vilda
  • Paul Clapham
  • Bear Bibeault
  • Jeanne Boyarsky
Sheriffs:
  • Ron McLeod
  • Tim Cooke
  • Devaka Cooray
Saloon Keepers:
  • Tim Moores
  • Tim Holloway
  • Jj Roberts
  • Stephan van Hulst
  • Carey Brown
Bartenders:
  • salvin francis
  • Scott Selikoff
  • fred rosenberger

Why no compiler ambiguity on reference?

 
Ranch Hand
Posts: 391
8
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Why doesn't the compiler complain below about an ambiguous (declaration) reference when attempting to resolve Inner when it is both a top level class and an inner/member class?


(I added the top level class to a Sybex CSG code example and both compiled and ran it.)

a complicated way to print Hi three times



 
Marshal
Posts: 70689
288
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
There must be some rule or other in the JLS for disambiguating such a situation. Only I can't remember seeing it.
 
author & internet detective
Posts: 40241
819
Eclipse IDE VI Editor Java
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Charles,
That line is not actually ambitious.  Try commenting out your inner class. If you do, this line doesn't compile at all


The reason is because outer.newInner() tells the compiler you intend to use an inner class.

The other new Inner() reference does still compiles. It refers to the top level class when the inner one no longer exists. So for that one, it uses the most specific match it can find.
 
Saloon Keeper
Posts: 12431
269
  • Likes 1
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Jeanne, I think the ambiguity that Charles is referring to is not in the initialization of the inner variable, but in the formal type of the variable declaration itself. If you removed outer.new Inner() from the declaration of Inner inner, Inner would still refer to Outer.Inner.

Java resolves the ambiguity by using the type in the deepest scope that encloses the variable declaration. The dirty details are in chapters 6.3 and 6.5 of the JLS. I'll see if I can quote the relevant parts after dinner.
 
Charles O'Leary
Ranch Hand
Posts: 391
8
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator

Stephan van Hulst wrote:Jeanne, I think the ambiguity that Charles is referring to is not in the initialization of the inner variable, but in the formal type of the variable declaration itself. If you removed outer.new Inner() from the declaration of Inner inner, Inner would still refer to Outer.Inner.

Java resolves the ambiguity by using the type in the deepest scope that encloses the variable declaration. The dirty details are in chapters 6.3 and 6.5 of the JLS. I'll see if I can quote the relevant parts after dinner.

Yep!  I hope this isn't an exam question!  
 
Jeanne Boyarsky
author & internet detective
Posts: 40241
819
Eclipse IDE VI Editor Java
  • Likes 1
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Ah. I missed the point of the question.

And no, they won't put two of the same class in the same question like this.
 
Stephan van Hulst
Saloon Keeper
Posts: 12431
269
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
So I said I would quote the relevant parts after dinner, but not exactly when after dinner. Anyway, I had my dinner. :P

§6.3 says:

The scope of a declaration is the region of the program within which the entity declared by the declaration can be referred to using a simple name, provided it is not shadowed (§6.4.1).



§6.4.1 says:

A declaration d of a type named n shadows the declarations of any other types named n that are in scope at the point where d occurs throughout the scope of d.



The declaration of Outer.Inner named Inner shadows the top level class Inner throughout the scope of Outer.Inner, i.e. inside the entire body of Outer.

Because Outer.Inner shadows the top level class Inner, the simple name "Inner" can not be used to refer to the top level class Inner from within the body of Outer, even though the top level class Inner is in scope. Instead, the simple name "Inner" will refer to the nested class Outer.Inner.
 
Campbell Ritchie
Marshal
Posts: 70689
288
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
If there is no package name, how could you refer to the top‑level class Inner from inside Outer? If at all.
 
Stephan van Hulst
Saloon Keeper
Posts: 12431
269
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
You can't.
 
Campbell Ritchie
Marshal
Posts: 70689
288
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Thought not.
 
Charles O'Leary
Ranch Hand
Posts: 391
8
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Super Thanks Stephan, Campbell, and Jeanne!
 
a wee bit from the empire
Building a Better World in your Backyard by Paul Wheaton and Shawn Klassen-Koop
https://coderanch.com/wiki/718759/books/Building-World-Backyard-Paul-Wheaton
reply
    Bookmark Topic Watch Topic
  • New Topic