疯狂java


您现在的位置: 疯狂软件 >> 新闻资讯 >> 正文

Java内部类使用


 

   

  一、什么是内部类?

  一个类的定义放在另一个类的内部,这个类就叫做内部类

  二、内部类有那些特性?

  1、内部类仍然是一个独立的类,在编译之后内部类会被编译成独立的.class文件,但是前面冠以外部类的类名和$符号 。

  2、内部类不能用普通的方式访问。内部类是外部类的一个成员,因此内部类可以自由地访问外部类的成员变量,无论是否是private的 。

  3、内部类声明成静态的,就不能随便的访问外部类的成员变量了,此时内部类只能访问外部类的静态成员变量 。

  三、内部类有哪几种?

  1.成员内部类

  如:

  复制代码

  1 package com.test01;

  2

  3 public class A {

  4 // 内部类 B 继承 TestPojo 和实现 TestInterface 接口

  5 class B extends TestPojo implements TestInterface{

  6 //内部类 B 自己的方法

  7 public void run(){

  8 System.out.println("我正在跑!");

  9 }

  10 //重写的接口方法

  11 public void testf() {

  12 System.out.println("实现接口!");

  13 }

  14 }

  15 // 方法里面调用内部类

  16 public void test(){

  17 B b = new B() ;

  18 b.testf() ; // 掉用重写接口方法

  19 b.run() ;  // 调用自己的方法

  20 b.testpojo() ; // 调用继承父类的方法

  21 }

  22 // main 方法测试

  23 public static void main(String[] args) {

  24 A a = new A() ;

  25 a.test() ;

  26 }

  27 }

  28 // 定义了一个接口 ,方法为testf()

  29 interface TestInterface{

  30 public void testf() ;

  31 }

  32 // 定义了一个普通类 方法testpojo()

  33 class TestPojo{

  34 public void testpojo(){

  35 System.out.println("我是简单的pojo类");

  36 }

  37 }

  38 // 实现 调用内部类里面的方法

  39 class Textone{

  40 public static void main(String[] args) {

  41 A.B b = new A().new B() ; //调用类A里面的内部类B

  42 /** 等同于 下面代码

  43 * A a = new A() ;

  44 * A.B b = a.new B() ;

  45 * */

  46 b.testf() ; // 掉用重写接口方法

  47 b.run() ; // 调用自己的方法

  48 b.testpojo() ; // 调用继承父类的方法

  49 }

  50 }

  复制代码

  2、方法内部类

  复制代码

  1 package com.test01;

  2

  3 public class PerTest {

  4 public void test(){ // 定义一个方法

  5 class Ne{ // 定义一个方法内部类

  6 public void fle(){ // 定义方法内部类的方法

  7 System.out.println("我正在飞翔!");

  8 }

  9 } ;

  10 new Ne().fle() ; //调用内部类的方法

  11 }

  12 public static void main(String[] args) {

  13 new PerTest().test() ; //测试

  14 }

  15 }

  复制代码

  注意: (1)、方法内部类只能在定义该内部类的方法内实例化,不可以在此方法外对其实例化。

  (2)、方法内部类对象不能使用该内部类所在方法的非final局部变量。

  因为方法的局部变量位于栈上,只存在于该方法的生命期内。当一个方法结束,其栈结构被删除,

  局部变量成为历史。但是该方法结束之后,在方法内创建的内部类对象可能仍然存在于堆中!

  例如,如果对它的引用被传递到其他某些代码,并存储在一个成员变量内。正因为不能保证局部变

  量的存活期和方法内部类对象的一样长,所以内部类对象不能使用它们。 (该理解来源于百度百科)

  3、匿名内部类

  1)、抽象匿名内部类

  复制代码

  1 package com.anonymous;

  2

  3 public class AbstractClass {

  4 public void test(){ //方法为test

  5 TestA a = new TestA(){ //实现抽象类

  6 @Override

  7 public void run() { //实现抽象类的方法

  8 System.out.println("我正在使用抽象匿名内部类");

  9 }

  10 } ;

  11 a.run() ; //调用内部类的方法

  12 }

  13 public static void main(String[] args) {

  14 new AbstractClass().test() ; //测试

  15 }

  16 }

  17 //定义一个抽象类 TestA 抽象方法为run()

  18 abstract class TestA{

  19 public abstract void run() ;

  20 }

  复制代码

  2)、接口匿名内部类

  复制代码

  1 package com.anonymous;

  2

  3 public class TestAnonymous {

  4 MyInterface m = new MyInterface(){ //实现接口

  5 public void eat() { //重写MyInterface 接口方法

  6 System.out.println("我正在吃饭!");

  7 }

  8 } ;

  9 public void ss(){ //方法ss

  10 m.eat() ; //调用重写的方法

  11 }

  12 public static void main(String[] args) {

  13 new TestAnonymous().ss() ; //测试

  14 }

  15 }

  16 //定义一个接口 方法为 eat

  17 interface MyInterface{

  18 public void eat() ;

  19 }

  复制代码

  注意:匿名内部 类 可以定义在方法内也可以定义在类的成员中,不管是那种匿名内部类都不能被外部类直接调用

  四、内部类的作用?

  每个内部类都能独立地继承自一个(接口的)实现,所以无论外围类是否已经继承了某个(接口的)实现,对于内部类都没有影响。如果没有

  内部类提供的可以继承多个具体的或抽象的类的能力,一些设计与编程问题就很难解决。从这个角度看,内部类使得多重继承的解决方案变得完整。

  接口解决了部分问题,而内部类有效地实现了“多重继承”。