• 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:
  • Tim Cooke
  • Campbell Ritchie
  • paul wheaton
  • Ron McLeod
  • Devaka Cooray
Sheriffs:
  • Jeanne Boyarsky
  • Liutauras Vilda
  • Paul Clapham
Saloon Keepers:
  • Tim Holloway
  • Carey Brown
  • Piet Souris
Bartenders:

Inner Class

 
Ranch Hand
Posts: 509
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
What is the significance of adding access modifier to Inner classses?



here Outer can be accessed by all classes, that means Inner also can be accessed by all classes or else it can be accessed in the same package because of default access??
 
Ranch Hand
Posts: 352
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
The inner class may only be accessed by other classes only through an instance of the outer class. However if there are attributes in the outer class you wish to keep public but still hide the inner class from external instantiation, then here is a reason for inner class access modifiers.





So in your case your inner class is exposed to all classes in your package (as it is deault access) so in your case:



..may indeed be called from any class within the same package.
 
Sheriff
Posts: 9708
43
Android Google Web Toolkit Hibernate IntelliJ IDE Spring Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
It is as simple as a general declaration in a class. Just look at this class



Now class MyExp cal be accessed anywhere, but the method myMethod can be accessed only inside the package of MyExp. Same is the case with inner classes...
 
Abhi vijay
Ranch Hand
Posts: 509
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Thanks again.
 
Ranch Hand
Posts: 1032
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Yeah, Ankit is right. Non-static inner classes are just instance members of the class they are in. And static inner classes are just static members of the class they are in. Let me know if you think this is wrong.
 
Stephen Davies
Ranch Hand
Posts: 352
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Just to add to Rubens point, static inner classes are actually treated by the JVM as a top-level class.
 
Ankit Garg
Sheriff
Posts: 9708
43
Android Google Web Toolkit Hibernate IntelliJ IDE Spring Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Stephen Davies wrote:Just to add to Rubens point, static inner classes are actually treated by the JVM as a top-level class.



But they have to referred with the syntax OuterClass.Inner class syntax and they can have protected or private visibility which a top level class can't have...
 
Stephen Davies
Ranch Hand
Posts: 352
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Yes static inner classes may be instantiated as such, but its not in a relationship with the outer instance (object to object), its only tied to the class itself.



According to Javaranch.com see: http://www.javaranch.com/campfire/StoryInner.jsp


"static inner classes aren't even supposed to be called inner classes at all. Technically, they are "top-level nested classes"



Also static inner classes may only access the static members of the outer Class (not instance). I am uncertain if they can recieve the private and protected access modifiers especially if they are treated as top-level classes. But Im sure one of the Bartenders here could clarify this?

Hope this helps.





 
Ranch Hand
Posts: 580
Eclipse IDE
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Stephen Davies wrote: I am uncertain if they can recieve the private and protected access modifiers especially if they are treated as top-level classes.







In this link , just before they talk about static inner class , they are telling that a non-static inner class can be instanitated as,
Inner i = new Outer().new Inner();
Is it possible this way??
I think it should be Outer.Inner i = new Outer().new Inner();
 
Stephen Davies
Ranch Hand
Posts: 352
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Thanks for clearing that up, James ,it does indeed compile. I suppose, its to do with the fact that even though they are inner classes they remain attrubutes of the outer class, and thus may be protected as such.

As for the example of Instantiating an inner class as in the Java Ranch Example, you can provide:



As you are intitializing the Outer and Inner class at the same time, and as the inner class requires the outer, its perfectly fine to instantiate the reference i in this way.

 
James Tharakan
Ranch Hand
Posts: 580
Eclipse IDE
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Stephen Davies wrote: I suppose, its to do with the fact that even though they are inner classes they remain attrubutes of the outer class, and thus may be protected as such.



Thats right.
And about, Inner i = new Outer().new Inner(); ,
I am worried about the LHS of the statement. How can we directly say ,
Inner i ???
ISn't that : Outer.Inner i;

 
Stephen Davies
Ranch Hand
Posts: 352
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
But isn't i just a reference variable, to an Inner object?
 
James Tharakan
Ranch Hand
Posts: 580
Eclipse IDE
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Stephen Davies wrote:But isn't i just a reference variable, to an Inner object?






My doubt is HOW can we say inner, without the class name of Outer.( Inner class is a non -static class)
 
Stephen Davies
Ranch Hand
Posts: 352
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

My doubt is HOW can we say inner, without the class name of Outer.( Inner class is a non -static class)


We are doing that:

 
James Tharakan
Ranch Hand
Posts: 580
Eclipse IDE
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator


Then why is this an error???
 
Ankit Garg
Sheriff
Posts: 9708
43
Android Google Web Toolkit Hibernate IntelliJ IDE Spring Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
well James the code that you gave will not work. You can access the static inner class by it's name in the original example as the initialization code and the static inner class were in the same class. So your code will not work while this will



Also Stephen you are right that static inner classes are treated like top level classes so they must not have private accessibility. And indeed the static inner classes or any other inner classes have no private or protected accessibility. What happens is a trick done by the compiler by changing the accessibility of the constructor of the static innre class. I had experimented on this using decompilation and reflection some time ago but I'm unable to recall it right now...
 
Stephen Davies
Ranch Hand
Posts: 352
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Well I stand corrected, you are indeed correct James, no matter what way one tweaks the code it doesn't want to compile without the instance of outer!! So there is an error in the tutorial (unless we are missing something). The following comiples fne:



 
Ruben Soto
Ranch Hand
Posts: 1032
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Ankit Garg wrote:
Also Stephen you are right that static inner classes are treated like top level classes so they must not have private accessibility. And indeed the static inner classes or any other inner classes have no private or protected accessibility. What happens is a trick done by the compiler by changing the accessibility of the constructor of the static innre class. I had experimented on this using decompilation and reflection some time ago but I'm unable to recall it right now...


Nice discussion, guys.
Ankit, what do you mean by the statements marked in bold? I'm afraid that you lost me there. Can't proper (non-static) inner classes be marked private and protected? Also, how does the constructor discussion apply here? I'm just missing what you are trying to say.
 
James Tharakan
Ranch Hand
Posts: 580
Eclipse IDE
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Ankit Garg wrote: well James the code that you gave will not work

.

well, that was the point of discussion. I was trying to say that it will NOT work.
Look in to this page , just before they talk about static inner classes,they said we can create an inner object llike this-----

campfire wrote:You can also instantiate both the outer class and inner class at the same time:

Inner i = new Outer().new Inner();

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

class Outer{

class Inner{}

}

class Test{



public static void main(String[] args){

new Test().fun();
}

void fun(){
Outer.Inner i= new Outer().new Inner(); // yes wee need Outer.Inner i
}
}


I think we need Outer.Inner on left side when creating object of inner class because here object is not being created in Outer class.It is created in Test class,may be we need to tell the compiler where is our inner class when creating the inner class object outside outer class.
If we create the inner class object in outer class then



will work.If I am wrong kindly correct me.


Regards
Sunny Mattas
SCJP5


 
James Tharakan
Ranch Hand
Posts: 580
Eclipse IDE
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

If we create the inner class object in outer class then



1. Inner i= new Outer().new Inner();



will work.If I am wrong kindly correct me.



you are not wrong.BUT, you dont need a outer class object to create an inner class object inside the outer class.
 
Sunny Mattas
Ranch Hand
Posts: 45
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

you don't need a outer class object to create an inner class object inside the outer class.



I think we still need a outer class object to create an inner class object inside the outer class when our inner class is not static because static inner classes are like separate classes.But non static regular inner class is member of outer class.

this is an extract from Kathy book

To create an instance of an inner class, you must have an instance of the outer class
to tie to the inner class. There are no exceptions to this rule: an inner class instance
can never stand alone without a direct relationship to an instance of the outer class.



Yes outer class object can be created in other classes i.e. not in outer class and then inner class object can be created in outer class.
But I think bottom line is we need a outer class object when we create a regular inner class .

If I am missing something please correct me.

Regards
Sunny Mattas
SCJP5
 
James Tharakan
Ranch Hand
Posts: 580
Eclipse IDE
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Sunny Mattas wrote: I think we still need a outer class object to create an inner class object inside the outer class when our inner class is not static



 
Sunny Mattas
Ranch Hand
Posts: 45
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

James Tharakan wrote:
class outer{
inner i= new inner();
class inner{

}
}

It is not always requried to have a outer class object to create a inner class object.



Here we are.Now can we use reference i with out creating object of outer class?



Above code is legal.But there's already an
instance of the outer class—the instance running the makeInner() method.Non static regular inner class is part of outer class just like any other part of class,so may be it needs a object on heap to work with.

above code will work.

but this won't


Regards
Sunny Mattas
SCJP5
 
James Tharakan
Ranch Hand
Posts: 580
Eclipse IDE
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Sunny Mattas wrote: I think we still need a outer class object to create an inner class object inside the outer class when our inner class is not static



You were talking about creating a inner class object. thats why i said YES.
But NOT about using the inner class object
 
Ruben Soto
Ranch Hand
Posts: 1032
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
For regular (non-static) inner classes you always need an associated instance of the enclosing class. This is the same as saying that you can't instantiate an inner class object from a static context. The trick is that sometimes the enclosing class instance is not explicit (there is an implicit this reference when you are in an instance context of the class.)
 
Ankit Garg
Sheriff
Posts: 9708
43
Android Google Web Toolkit Hibernate IntelliJ IDE Spring Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Ruben Soto wrote:

Ankit Garg wrote:
Also Stephen you are right that static inner classes are treated like top level classes so they must not have private accessibility. And indeed the static inner classes or any other inner classes have no private or protected accessibility. What happens is a trick done by the compiler by changing the accessibility of the constructor of the static innre class. I had experimented on this using decompilation and reflection some time ago but I'm unable to recall it right now...


Nice discussion, guys.
Ankit, what do you mean by the statements marked in bold? I'm afraid that you lost me there. Can't proper (non-static) inner classes be marked private and protected? Also, how does the constructor discussion apply here? I'm just missing what you are trying to say.



Ruben what I meant to say is that every inner class is converted into a normal class. Although in your source code you can mark an inner class as private or protected, but we know that it will get converted into a normal top level class. So what I meant to say was that when the compiler converts a private inner class into a top level class, it plays with the access modifier of the constructor of the inner turned outer class to implement the private thing. This is fairly complicated and even I couldn't figure it out completely but one thing is for sure, SCJP won't cover this detail
 
Ruben Soto
Ranch Hand
Posts: 1032
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
OK Ankit now I understand what you are saying. Definitely not something that I'm going to study for the exam, but very interesting.
 
Ankit Garg
Sheriff
Posts: 9708
43
Android Google Web Toolkit Hibernate IntelliJ IDE Spring Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Ruben actually I couldn't come to any decision as there is a lot of difference between different ways of looking at the inner class after compilation. Some decompilers show the inner class as private and some show then package visible and their constructor as private. If you use javap command on the inner class name, then it will show the inner class as package visible. I also tried reflection and as far as I remember, it also showed that the class is package visible and the constructor is private or something and there is a factory method or something. But I don't remember it completely so you can try the reflection thing and I'll try that again when I get some time
 
Ruben Soto
Ranch Hand
Posts: 1032
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
You certainly put some very impressive efforts in looking into this... When you get to such a low level it is interesting to see how things are really implemented, and many times it is something completely different to what you might have imagined.
 
Stephen Davies
Ranch Hand
Posts: 352
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I agree wholeheartedly, discussions such as this, allow us to discus some interesting core fundamental aspect of Java, great discussion!

 
With a little knowledge, a cast iron skillet is non-stick and lasts a lifetime.
reply
    Bookmark Topic Watch Topic
  • New Topic