The definition of one class can be placed inside the definition of another class, which is called an inner class.

Inner classes are a very useful feature, but one that is a little harder to understand and use (I have only a passing acquaintance with inner classes).

First meeting

Inner classes are very easy to understand from the outside, which is nothing more than defining a class inside a class.

 

1 public class OuterClass { 2 private String name ; 3 private int age; 4 5 public String getName() { 6 return name; 7 } 8 9 public void setName(String name) { 10 this.name = name; 11 } 12 13 public int getAge() { 14 return age; 15 } 16 17 public void setAge(int age) { 18 this.age = age; 19 } 20 21 class InnerClass{ 22 public InnerClass(){ 23 name = "chenssy"; 24 age = 23; 25} 26} 27}Copy the code

 

InnerClass is the InnerClass. We don’t use InnerClass very much for beginners, but as we get better at programming, we begin to understand the InnerClass’s power. It allows us to design our programs more elegantly. Before we use inner classes, we need to understand why we use inner classes and what benefits they can bring us.

Why use inner classes

Why use inner classes? There’s a quote in Think in Java that says the most interesting thing about using inner classes is that each inner class inherits an implementation independently, so it doesn’t matter if the outer class already inherits an implementation.

In our programming sometimes there are some problems that are difficult to solve using interfaces, this time we can use the inner class provided by the ability to inherit multiple concrete or abstract classes to solve these programming problems. It is safe to say that interfaces are only part of the solution, while inner classes complete the solution for multiple inheritance.

 

 1 public interface Father {
 2 
 3 }
 4 
 5 public interface Mother {
 6 
 7 }
 8 
 9 public class Son implements Father, Mother {
10 
11 }
12 
13 public class Daughter implements Father{
14 
15     class Mother_ implements Mother{
16         
17     }
18 }
Copy the code

 

We really don’t see any advantage in using inner classes in this example, but what if Father and Mother are not interfaces, but abstract or concrete classes? At this point we have to use inner classes to implement multiple inheritance.

The biggest advantage of using inner classes is that they solve multiple inheritance problems very well, but if we don’t need to solve multiple inheritance problems, we can naturally use other coding methods, but using inner classes also gives us the following features (from Think in Java) :

An inner class can have multiple instances, each of which has its own state information and is independent of the information of other peripheral objects.

2. Within a single enclosing class, you can have multiple inner classes implement the same interface in different ways, or inherit from the same class.

3. The time at which the inner class object is created does not depend on the creation of the outer class object.

4. An inner class does not have a confusing IS-A relationship; it is a separate entity.

5. The inner class provides better encapsulation and is not accessible to any other class except the enclosing class.

Second, the internal class basis

This section focuses on how inner classes use properties and methods of outer classes, and use.this and.new.

When we create an inner class, it has an implicit relationship with the outer class, and depending on this relationship, it has unlimited access to the elements of the outer class.

 

1 public class OuterClass { 2 private String name ; 3 private int age; 7 public class InnerClass{8 public InnerClass(){9 name = "chenssy"; 10 age = 23; 13 public void display(){14 system.out.println ("name: "+ getName() +"; + getAge(); 15 } 16 } 17 18 public static void main(String[] args) { 19 OuterClass outerClass = new OuterClass(); 20 OuterClass.InnerClass innerClass = outerClass.new InnerClass(); 21 innerClass.display(); 22}} 23 24 -- -- -- -- -- -- -- -- -- -- -- -- -- -- 25 Output: name: 26 chenssy; Age: 23Copy the code

 

In this application, we can see that the InnerClass seamlessly accesses the properties of the OuterClass, even though it’s private. This is because when we create an inner class object of a enclosing class, the inner class object must capture a reference to that enclosing class object, and whenever we access a member of the enclosing class, we will use that reference to select the member of the enclosing class.

In fact in this application we also saw how to refer to the inner class: we need to specify the type of the object reference inner class: OuterClasName. InnerClassName. Outerclass.innerclass InnerClass = outerClass.new InnerClass(); OuterClass = outerClass.new InnerClass(); .

We can also use outerClassname.this if we need to generate a reference to an external class object. This will generate a reference to the external class correctly. Of course, this is known at compile time, with no run-time costs.

 

1 public class OuterClass { 2 public void display(){ 3 System.out.println("OuterClass..." ); 4 } 5 6 public class InnerClass{ 7 public OuterClass getOuterClass(){ 8 return OuterClass.this; 9 } 10 } 11 12 public static void main(String[] args) { 13 OuterClass outerClass = new OuterClass(); 14 OuterClass.InnerClass innerClass = outerClass.new InnerClass(); 15 innerClass.getOuterClass().display(); 16 } 17 } 18 ------------- 19 Output: 20 OuterClass...Copy the code

 

An inner class is a compile-time concept, and once compiled, it is a completely different class from the outer class (although they are still related to each other). For an OuterClass named OuterClass and an InnerClass named InnerClass, two class files appear after a successful compilation: outerclass. class and OuterClass$innerclass.class.

Inner classes in Java are mainly divided into member inner classes, local inner classes, anonymous inner classes, static inner classes.

Intra-member classes

Member inner class is also the most common inner class, it is a member of the outer class, so it is unlimited access to all member attributes and methods of the outer class, although it is private, but the outer class to access the inner class member attributes and methods need to access through the inner class instance.

There are no static variables or methods in a member inner class. Second: the member inner class is attached to the enclosing class, so the inner class can be created only if the enclosing class is created first.

 

1 public class OuterClass { 2 private String str; 3 4 public void outerDisplay(){ 5 System.out.println("outerClass..." ); 6} 7 8 public class InnerClass{9 public void innerDisplay(){10 STR = "chenssy..." ; 12 System.out.println(str); 14 outerDisplay(); 15} 16} 17 18 /* It is recommended to use getxxx() to get the member inner class, */ 19 public InnerClass getInnerClass(){20 return new InnerClass(); 21 } 22 23 public static void main(String[] args) { 24 OuterClass outer = new OuterClass(); 25 OuterClass.InnerClass inner = outer.getInnerClass(); 26 inner.innerDisplay(); 27 } 28 } 29 -------------------- 30 chenssy... 31 outerClass...Copy the code

 

It is recommended to use getxxx() to get a member inner class, especially if the inner class’s constructor has no arguments.

Local inner class

Have so a kind of inner class, it is nested within the methods and effects on, for the use of this class is mainly used to solve more complex problems, want to create a class to support our solution, then again don’t want this class are available for the public, so was born the local inner classes, as well as local inner classes and members of the inner class is compiled, However, its scope has changed, and it can only be used in the method and property, outside the method and property will be invalid.

I couldn’t Think of a good example for a local inner class, so I used the classic example from Think in Java.

Defined in a method:

 

1 public class Parcel5 { 2 public Destionation destionation(String str){ 3 class PDestionation implements Destionation{ 4 private String label; 5 private PDestionation(String whereTo){ 6 label = whereTo; 7 } 8 public String readLabel(){ 9 return label; 10 } 11 } 12 return new PDestionation(str); 13 } 14 15 public static void main(String[] args) { 16 Parcel5 parcel5 = new Parcel5(); 17 Destionation d = parcel5.destionation("chenssy"); 18}} 19Copy the code

 

Define in scope:

 

1 public class Parcel6 { 2 private void internalTracking(boolean b){ 3 if(b){ 4 class TrackingSlip{ 5 private String id;  6 TrackingSlip(String s) { 7 id = s; 8 } 9 String getSlip(){ 10 return id; 11 } 12 } 13 TrackingSlip ts = new TrackingSlip("chenssy"); 14 String string = ts.getSlip(); 15 } 16 } 17 18 public void track(){ 19 internalTracking(true); 20 } 21 22 public static void main(String[] args) { 23 Parcel6 parcel6 = new Parcel6(); 24 parcel6.track(); 26 25}}Copy the code

 

Anonymous inner classes

In Swing programming, we often use this approach to bind events

 

1 button2.addActionListener( 2 new ActionListener(){ 3 public void actionPerformed(ActionEvent e) { 4 System.out.println(" You pressed button 2 "); 5}});Copy the code

 

This may seem strange at first, because the inner class has no name, but look at this example:

 

1 public class OuterClass { 2 public InnerClass getInnerClass(final int num,String str2){ 3 return new InnerClass(){ 4 int number = num + 3; 5 public int getNumber(){ 6 return number; 7}}; Public static void main(String[] args) {12 OuterClass out = new OuterClass(); 13 InnerClass inner = out.getInnerClass(2, "chenssy"); 14 System.out.println(inner.getNumber()); 15 } 16 } 17 18 interface InnerClass { 19 int getNumber(); 20 } 21 22 ---------------- 23 Output:Copy the code

 

Here we need to look at a couple of places

1. Anonymous inner classes have no access modifiers.

2. New anonymous inner class, which should exist in the first place. If we comment out the InnerClass interface, we get a compilation error.

3. Notice the getInnerClass() parameter. The first parameter is final, but the second parameter is not. We also find that the second parameter is not used in the anonymous inner class, so when the method parameter needs to be used by the anonymous inner class, the parameter must be final.

Anonymous inner classes have no constructors. Because it doesn’t even have a name to construct.

PS: Due to the lack of space, I will cover anonymous inner classes here. I will cover more details about anonymous inner classes in the next blog post, including why parameters should be defined as final, how to initialize anonymous inner classes, and so on.

 

Static inner class

Static can modify member variables, methods, code blocks, and other inner classes. Static inner classes that use static modifiers are called static inner classes, but we prefer to call them nested inner classes. One of the biggest differences between a static inner class and a non-static inner class is that a non-static inner class implicitly stores a reference to the enclosing enclosing it after compilation, whereas a static inner class does not. The absence of this reference means:

1. Its creation does not depend on the enclosing class.

2. It cannot use non-static member variables and methods of any enclosing class.

 

1 public class OuterClass { 2 private String sex; 3 public static String name = "chenssy"; InnerClass1{9 public static String _name1 = 9 public static String _name1 = 9 public static String _name1 = "chenssy_static"; 11 12 public void display(){13 /* 14 * Static inner classes can only access static member variables and methods of the outer class. 15 * Cannot access non-static member variables and methods of the outer class. 16 */ 17 System.out.println("OutClass name :" + name); InnerClass2{25 /** innerclass cannot have a static member */ 26 public String _name2 = "chenssy_inner"; */ 28 public void display(){29 system.out.println ("OuterClass name: "+ name); 35 * @author chenssy 36 * @data 2013-10-25 37 * @return void 38 */ 39 public void 38 Display (){40 /* Outer classes access static inner classes: inner classes. */ 41 system.out.println (innerclass._name1); 42 /* Static inner classes can create instances directly without relying on outer classes */ 43 new InnerClass1().display(); 46 outerclass.innerclass2 () = new OuterClass().new innerclass (); 47 /* Members of orientation non-static inner classes need to use instances of non-static inner classes */ 48 system.out.println (inner2._name2); 49 inner2.display(); 50 } 51 52 public static void main(String[] args) { 53 OuterClass outer = new OuterClass(); 54 outer.display(); 55 } 56 } 57 ---------------- 58 Output: 59 CHensSY_static 60 OutClass name :chenssy 61 CHensSY_inner 62 OuterClass name :chenssyCopy the code

 

This example illustrates the difference between static and non-static inner classes.

This is the end of the inner class! In fact, I know the inner class is only fur, cognition is limited! I will use these days to study the inner class!