Win a copy of Murach's Python Programming this week in the Jython/Python forum!
  • Post Reply Bookmark Topic Watch Topic
  • New Topic

Are members in a static nested class implicitly static?  RSS feed

 
Edwardd Lee
Greenhorn
Posts: 18
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
I can't seem to find any information about this online. In my opinion, since there can only be one copy of a static nested class across all instances of its enclosing class, there should also be only one copy of the members inside the static nested class, therefore making them implicitly static. Is this correct?
 
Junilu Lacar
Sheriff
Posts: 10879
158
Android Debian Eclipse IDE IntelliJ IDE Java Linux Mac Spring Ubuntu
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
No, that's not correct. A static nested class has more or less the same semantics as a regular top-level class but with the additional scope of its enclosing class. See https://docs.oracle.com/javase/tutorial/java/javaOO/nested.html

There is an example in that tutorial where a nested class is instantiated with the statement new OuterClass.StaticNestedClass(). If you added a static import declaration in the program, import static OuterClass.StaticNestedClass;, you could instantiate the nested class just as you would any other top-level class and you couldn't tell the difference.

 
Edwardd Lee
Greenhorn
Posts: 18
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Please correct me if I'm wrong, but I think the whole point of making a variable static is to ensure that only one copy of it exists, regardless of how many objects are created. Therefore, I can call OuterClass.StaticNestedClass A = new OuterClass.StaticNestedClass();   OuterClass.StaticNestedClass B = new OuterClass.StaticNestedClass();   OuterClass.StaticNestedClass C = new OuterClass.StaticNestedClass();   however many times I want and there will only be one copy of StaticNestedClass. Therefore, any members inside the StaticNestedClass should only have one copy too. Doesn't that make them implicitly static?
 
Junilu Lacar
Sheriff
Posts: 10879
158
Android Debian Eclipse IDE IntelliJ IDE Java Linux Mac Spring Ubuntu
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
You are confusing a static member with a static variable. A static nested class is not a variable of the enclosing class. When the nested class is loaded, it is loaded just like any other class would be loaded except it has an additional scoping restriction in that its name must be prefixed by the enclosing class name.  The fact that the nested class is declared as static implies *absolutely nothing* about its own members being static or not. That's still dictated by whether or not the static keyword is used to declare the member in the static nested class. The nested class can still have its own static members and instance members.

Again, you are incorrect in thinking that just because the nested class is declared as static, all its members are implicitly static. That's *not* how it works.
 
Junilu Lacar
Sheriff
Posts: 10879
158
Android Debian Eclipse IDE IntelliJ IDE Java Linux Mac Spring Ubuntu
  • Likes 1
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Here's an example program for you to study. The static nested class is Journal.Entry. You can see on line 42 that this nested class is instantiated multiple times. Nothing in the Journal.Entry is implicitly static; in fact, nothing in that class is static. All its members are instance members.

This is the output when you run this program:

Journal: Personal
Entry: Day 1
Went fishing

Entry: Day 2
Worked on boat

Entry: Day 3
Drove to beach

Entry: Day 4
Watched TV



Journal: Work
Entry: Monday
Meetings

Entry: Tuesday
Project work

Entry: Wednesday
Day Off

Entry: Thursday
Conference

Entry: Friday
Team lunch
 
Henry Wong
author
Sheriff
Posts: 22843
119
C++ Chrome Eclipse IDE Firefox Browser Java jQuery Linux VI Editor Windows
  • Likes 1
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Junilu Lacar wrote:
Again, you are incorrect in thinking that just because the nested class is declared as static, all its members are implicitly static. That's *not* how it works.


Agreed. Most programming languages reuse keywords -- otherwise, there would be too many reserve words in the language, or a large concern that more will be added (which breaks old code).

In this case, the "static" modifier can be used for fields, methods, or classes -- and arguably, they don't exactly do (mean) the same thing.

Henry 
 
Junilu Lacar
Sheriff
Posts: 10879
158
Android Debian Eclipse IDE IntelliJ IDE Java Linux Mac Spring Ubuntu
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
I'd advise you to think very hard about your design before using static nested classes.  They are very easy to get wrong and when you do, your design becomes very confusing and convoluted.  A nested class has a very tight relationship with its enclosing class and the semantics of that relationship should be along the lines of the Outer class "owning"/"containing"/"is made up of" instances of the static nested class. DO NOT just nest a class inside another without a good reason to do so. A BAD reason to nest a class would be solely for convenience.

There must be a logical relationship between a nested class and its enclosing class, otherwise, you should just declare them as separate classes until your design clearly dictates that one should be nested inside the other.
 
Edwardd Lee
Greenhorn
Posts: 18
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Hi Junilu,

Thanks for the detailed explanation and example! Here's my understanding after reading them, please correct me if I am wrong again: a static nested class is almost identical to top level classes, except that its name must be prefixed by the enclosing class name. You can create as many instances/copies of the static classes as you want. If my above understanding is correct, what is the point of using a static nested class? For instance, in your example code, the static nest class Entry could be easily written as a member inner class. What's the advantage then to make it a static nested class?
 
Campbell Ritchie
Sheriff
Posts: 53769
127
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Junilu Lacar wrote:. . .  A nested class has a very tight relationship with its enclosing class and the semantics of that relationship should be along the lines of the Outer class "owning"/"containing"/"is made up of" instances of the static nested class. . . .
I tend to think of it the other way; the objects of the nested class are “PARTS OF” the outer class object. That works nicely for Nodes in LinkedLists, but doesn't work so well for ActionListener classes inside a frame.
Edwardd Lee wrote:. . . a static nested class is almost identical to top level classes, . . .
Afraid that isn't correct. A public static nested class can easily be instantiated outside its enclosing type with new OuterClass.InnerClass(...); like a top level class, but nested classes have lots of differences from top level classes as you have already been told. Access to private members of the surrounding scope is one difference.

By the way: If you can instantiate a nested class with new OuterClass.InnerClass(...);, then that object has fields to match the constructor parameters and those fields would have different values for different instances ∴ those fields cannot be static. More about nested classes in the Java™ Tutorials.
 
Junilu Lacar
Sheriff
Posts: 10879
158
Android Debian Eclipse IDE IntelliJ IDE Java Linux Mac Spring Ubuntu
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Campbell Ritchie wrote:
Edwardd Lee wrote:. . . a static nested class is almost identical to top level classes, . . .
Afraid that isn't correct. A public static nested class...

That's the problem with analogies/similes, there's always a "but" in there where the analogy will fall apart. The nuance of the similarity, if you want to keep the analogy useful, is in the loading/referencing of the nested class. They are pretty much the same as top-level classes in that respect, except for the additional scoping restrictions on the static nested class.

To answer the question of what's the point of static nested class, you have to look at the semantics of the two classes and how closely related they are. The other example Campbell gave of a LinkedList and its Nodes is a good one. Again, you have to think very carefully about your design before you decide to make a class static and nested in another. It has to make sense semantically.  If you start manipulating instances of the static nested class outside of the enclosing class, then the decision to make the class a nested one becomes questionable. As in my example of a Journal.Entry and Campbell's example of a LinkedList.Node, any low-level manipulation of the nest class should be limited to the enclosing class itself. If you do it outside of this scope, then you're likely breaking encapsulation.
 
Campbell Ritchie
Sheriff
Posts: 53769
127
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
So, do we think that Map.Entry is a naughty bit of design, or does that not apply to interfaces?
 
Junilu Lacar
Sheriff
Posts: 10879
158
Android Debian Eclipse IDE IntelliJ IDE Java Linux Mac Spring Ubuntu
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Campbell Ritchie wrote:So, do we think that Map.Entry is a naughty bit of design, or does that not apply to interfaces?

I don't know. I guess I've always implicitly trusted that the designers of the standard Java library classes had good reasons for making the design choices they made about Map.Entry (but not the design of other classes like the old Date and Calendar classes, of course); I never really thought there was anything off with the decision to make Map.Entry a nested interface. If I'm not mistaken, a nested interface is implicitly static... yup, I guess I'm not old and decrepit yet after all: http://docs.oracle.com/javase/specs/jls/se8/html/jls-8.html#jls-8.5 (8.5.1)

I'd be interested to know if you know of any notable relevant discussions about Map.Entry. I might yet learn something new today.

 
Campbell Ritchie
Sheriff
Posts: 53769
127
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Junilu Lacar wrote:. . . I'd be interested to know if you know of any notable relevant discussions about Map.Entry. . . .
No, I don't, I am afraid. The thought about Map.Entry came to me all of a sudden when you started complaining about public nested classes.
And what about the two nested classes in Rectangle2D? Of course, some people say Swing is badly designed throughout. I recently decided to bite the bullet and learn JavaFX and I was pleasantly surprised about how much better the classes seem to be designed.
 
  • Post Reply Bookmark Topic Watch Topic
  • New Topic
Boost this thread!