• 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 Pie Elite all forums
this forum made possible by our volunteer staff, including ...
Marshals:
  • Campbell Ritchie
  • Tim Cooke
  • paul wheaton
  • Liutauras Vilda
  • Ron McLeod
Sheriffs:
  • Jeanne Boyarsky
  • Devaka Cooray
  • Paul Clapham
Saloon Keepers:
  • Scott Selikoff
  • Tim Holloway
  • Piet Souris
  • Mikalai Zaikin
  • Frits Walraven
Bartenders:
  • Stephan van Hulst
  • Carey Brown

Extend an inner class by code outside the top level class

 
Greenhorn
Posts: 22
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator


For the above code, the compile time error generated is :
No enclosing instance of type Main is available due to some intermediate constructor invocation.
Does this error indicate that there is some other way to extend an inner class by code outside the top level class?
Can someone help by explaining the error statement?
 
author
Posts: 23958
142
jQuery Eclipse IDE Firefox Browser VI Editor C++ Chrome Java Linux Windows
  • Likes 1
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Cyril Sadasivan wrote:

For the above code, the compile time error generated is :
No enclosing instance of type Main is available due to some intermediate constructor invocation.
Does this error indicate that there is some other way to extend an inner class by code outside the top level class?
Can someone help by explaining the error statement?



What is happening is... an inner class needs an instance of the outer class for it to be instantiated. [ORIGINAL EXPLANATION DELETED] ....... Never mind, here is a better way to think about it.... the subclass is not an inner class and hence, doesn't have an outer class, but its super class needs an outer class, so....

Anyway, to fix the problem, you need a constructor that uses an instance of the super class outer class.... like this....



Henry
 
Cyril Sadasivan
Greenhorn
Posts: 22
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Henry Wong wrote:


Henry



Thanks a lot Henry.
I got the concept..but i am not familiar with the idea of calling super() on a different object
 
Ranch Hand
Posts: 46
Eclipse IDE Slackware Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Note: I typed this all up, but then realized the topic got locked (for good reason). I'm just going to post my comment even though Henry has given you an answer.


Yes, there is a way. The rules get moderately complicated.

What you need to do is to pass a reference of an innermost enclosing parent class of a class that you are extending, and call its super(). So, let's expand on your example,



A class that you are extending is Main.Inner.NestedInner and its innermost enclosing parent is Main.Inner, so we must pass its reference to Demo's constructor.

"Since an inner object can not exist without an instance of the enclosing class, the constructor for the inner class should have the enclosing class as one of the arguments; this is automatically provided by the compiler generated code in the class file. In addition, the first statement in the constructor should invoke the super class constructor with the following syntax: <enclosing instance>. super(). If the inner class that is extended has several layers of nesting, the enclosing instance immediately above the inner class is passed."

Now, if the constructor of a class that is being extended passes arguments, due to inheritance rules, you should call that particular constructor rather than the default one (super()). You are allowed to pass arguments to an overloaded constructor of a class that is extending an external inner class -- it's just that you need to, as I said, first, pass the parent of an innerclass extending class, then call its super().
 
Henry Wong
author
Posts: 23958
142
jQuery Eclipse IDE Firefox Browser VI Editor C++ Chrome Java Linux Windows
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Yalvin Duha wrote:Note: I typed this all up, but then realized the topic got locked (for good reason). I'm just going to post my comment even though Henry has given you an answer.



Yeah. Agreed. If I had typed all that up, only to realize that the the OP had already gotten an answer due to cross-posting, I would not like it either..... Cyril, please don't do that again.

Henry
 
Cyril Sadasivan
Greenhorn
Posts: 22
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
i am sorry, i'm not much familiar with the forum..didn't know topics could get locked..
anyways thanks for all the help guys..
just going through all your replies on both the posts
 
Cyril Sadasivan
Greenhorn
Posts: 22
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
These are the points i gathered
-When an inner class is extended by code, outside the enclosing class, the extending class 'must write' a constructor which calls it's super class constructor through an instance of the outer class of the super class.
-The default contructor provided by the extended inner class will have 'super()' which will fail since super() in this case can be called only as an invocation on an outer class object.

just to make sure i understood, i wrote the below program.

Output:
 
Yalvin Duha
Ranch Hand
Posts: 46
Eclipse IDE Slackware Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Yes. The point is (but don't take my words on it and someone else should correct me if I'm wrong), since there is no reference to the enclosing parent of the inner class that is being extended, you have to explicitly either pass it to the constructor and invoke its super() or create a new instance of that parent class and call its super() inside of the constructor to instantiate it.

Because, after all, the inner class you are extending is simply a member of that enclosing parent class, and you need a reference to it in order to construct the inner class. And the compiler is definitely creating a bunch of synthetic object references, i.e. this$0, this$1, etc., for each of the enclosing classes and providing these references to the inner class. So, I'm assuming for some reason it doesn't create such reference for the enclosing parent class, and the programmer should do it explicitly for the compiler.

Maybe someone else can accurately detail the process.
 
Politics n. Poly "many" + ticks "blood sucking insects". Tiny ad:
Gift giving made easy with the permaculture playing cards
https://coderanch.com/t/777758/Gift-giving-easy-permaculture-playing
reply
    Bookmark Topic Watch Topic
  • New Topic