Java内部类:静态与非静态内部类
文章目录一、成员内部类非静态内部类基本用法特点二、静态嵌套类静态内部类基本用法成员内部类 vs 静态内部类 对比关键区别总结一、成员内部类非静态内部类成员内部类属于外部实例必须创建外部实例才能创建成员内部类实例基本用法publicclassjava{publicstaticvoidmain(String[]args){//创建内部类实例对象Outer.InnerinnernewOuter().newInner();System.out.println(inner.innerPrivate);inner.display();//成员内部类属于外部实例OuterouternewOuter();Outer.Innerinner1outer.newInner();Outer.Innerinner2outer.newInner();//测试内部类静态方法testStatic();}//java16以前不允许publicstaticvoidtestStatic(){//静态成员/方法独立于内部/外部类而存在,直接存于方法区System.out.println(Outer.Inner.innerStatic);Outer.Inner.methodStatic();}}classOuter{// 外部类成员变量privateintouterPrivate10;publicStringouterPublicPublic Outer;staticintouterStatic100;// 外部类成员方法publicvoidouterMethod(){System.out.println(Outer method called);}// 外部类静态方法publicstaticvoidouterStaticMethod(){System.out.println(外部类静态方法);}//访问内部成员方法publicvoidvisitInner(){InnerinnernewInner();inner.display();System.out.println(inner.innerPrivate);}// 成员内部类classInner{// 内部类成员变量publicintinnerPrivate20;//java15以前成员内部类不允许定义静态成员publicstaticintinnerStatic30;// 内部类成员方法publicvoiddisplay(){//隐式调用Outer.thisSystem.out.println(Outer private: outerPrivate);// 访问外部类私有成员System.out.println(Outer public: outerPublic);// 访问外部类公有成员System.out.println(Outer static: outerStatic);// 访问外部类静态成员outerMethod();// 调用外部类方法outerStaticMethod();// 调用外部类静态方法}//java15以前不允许publicstaticvoidmethodStatic(){System.out.println(Inner static called);}}}特点成员内部类可以访问外部类的所有成员包括private和static成员内部类属于外部实例,一个外部类实例可以有多个内部类实例必须先创建外部类实例才能创建内部类实例,内部类中可以使用Outer.this显式引用外部类实例java16以前成员内部类不允许定义静态成员/静态方法二、静态嵌套类静态内部类静态内部类static inner class不属于外部类的实例它更像是一个独立的类只是嵌套在另一个类的作用域内。可以把它理解为一个普通的类只是它的类名是 Outer.StaticInner而不是 StaticInner这也解释了为什么静态内部类只能调用外部类的静态成员基本用法publicclassjava{publicstaticvoidmain(String[]args){//实例创建Outer.StaticInnerinnernewOuter.StaticInner();inner.innerMethod();//内部类方法Outer.StaticInner.staticInnerMethod();//内部类静态方法}}classOuter{publicStringouterField外部类私有字段;publicstaticStringstaticOuterField外部类静态字段;publicvoidouterMethod(){System.out.println(外部类方法);}publicstaticvoidstaticOuterMethod(){System.out.println(外部类静态方法);}// 静态内部类staticclassStaticInner{privateStringinnerField静态内部类字段;privatestaticStringstaticInnerField静态内部类静态字段;publicvoidinnerMethod(){// 只能访问外部类的静态成员System.out.println(staticOuterField);staticOuterMethod();// 不能访问外部类的非静态成员// System.out.println(outerField); // 编译错误// outerMethod(); // 编译错误// 访问自己的成员System.out.println(innerField);System.out.println(staticInnerField);staticInnerMethod();}publicstaticvoidstaticInnerMethod(){//只能访问外部静态成员方法System.out.println(staticOuterField);staticOuterMethod();;}}}成员内部类 vs 静态内部类 对比特性成员内部类非静态内部类静态内部类依赖外部类实例✅ 必须依赖outer.new Inner()❌ 不依赖直接new Outer.Inner()访问外部类实例成员✅ 能访问包括private成员❌ 不能访问只能访问static成员访问外部类静态成员✅ 能访问✅ 能访问定义static成员java16以前不能除非static final常量java16后可以✅ 可以定义static方法/字段内存占用隐式持有外部类引用this$0不持有外部类引用更独立典型用途需要访问外部类实例的场景如事件监听工具类、Builder 模式、线程安全单例创建方式Outer outer new Outer();Outer.Inner inner outer.new Inner();Outer.Inner inner new Outer.Inner();关键区别总结依赖关系成员内部类必须绑定到外部类实例outer.new Inner()。静态内部类独立存在直接new Outer.Inner()。访问权限成员内部类可以访问外部类的所有成员包括private实例字段/方法。静态内部类只能访问外部类的static成员。静态成员支持成员内部类不能有static方法/字段除非是static final常量。静态内部类可以自由定义static成员。内存管理成员内部类隐式持有外部类引用可能导致内存泄漏。静态内部类不持有外部类引用更安全。