Java笔记十八.内部类和匿名类

来源:互联网 发布:苏州方正软件 编辑:程序博客网 时间:2024/06/10 10:50
内部类和匿名类
转载请表明出处:http://blog.csdn.net/u012637501(嵌入式_小J的天空)
一、内部类
1.定义
    在一个类内部定义类,即为嵌套类(内部类)。有如下几点特点:(1)嵌套类可以直接访问嵌套它的类的成员(变量和方法),包括private成员。但是,嵌套类的成员却不能被嵌套它的类直接访问。(2)内部类使得程序代码更为紧凑,程序更具模块化。
2.内部类实现方法
(1)类中定义和使用一个内部类
    在类中直接定义的嵌套类的使用范围,仅限于这个类的内部。内部类的定义和普通类的定义没有什么区别,内部类可以直接访问和引用它的外部类的所有变量和方法,就像外部类中的其他非static成员的功能一样,和外部类不同的是,内部类可以声明为private或protected
a.内部类被外部类引用
源码:innerClassDemo.java
//外部类class Outer{  String name="我是外部类成员变量";  void outerMethod()//在外部类定义一个成员方法,实现创建一个内部类实例并调用其成员方法  {   inner in=new inner();   in.dispaly();  }  //内部类  class inner  {   void display()   {    System.out.println("Method of inner class print 'name'="+name);   }  }}/*-------------------------------------------*/public class innerClassDemo { public static void main(String[] args) {  Outer outer = new Outer();  outer.outerMethod(); }}

打印信息:

分析:该源码实现了在外部类Outer中实现一个内部类inner,且在该内部类中定义一个成员方法来使用外部类的Outer的成员name。另外,只能在外部类Outer实例化内部类inner对象,在外部类之外实例化该内部类是不允许的,除非将inner声明为public(后面介绍)。
    从内存分布的角度分析,实际上在内部类对象保存了一个对外部类对象的引用(Outer.this),当内部类的成员方法中访问某一变量(方法)时,如果在该方法和内部类中都没有定义过这个变量调用就会被传递给内部类中保存的哪个外部类对象的引用。通过哪个外部类对象的引用调用这个变量(方法)。

注释:只有放this.变量不存在的情况下,传递给Outer.this.变量。
b.内部类被外部类以外的类引用
    内部类可以通过创建对象从外部类之外被调用.
(1)将内部类声明为public;
(2)在外部类以外的类,先创建一个外部类的实例再通过该实例创建内部类的实例
形式:
Outer outer = new Outer(); 
Outer.Inner inner=outer.new Inner(); 
源码:InnerClassDemo
//外部类class Outer{ private int number=100; public class Inner {  private int number=200;  void print(int number)  {   System.out.println("I am innerClass"+"\n"+"参数number="+number+"\n"+"内部类成员         number="+this.number+"\n"+"外部类成员number="+Outer.this.number);  } }}//外部以外的类public class InnerClassDemo { public static void main(String[] string) {  Outer outer = new Outer(); //实例化一个Outer对象  Outer.Inner inner=outer.new Inner();//实例化一个Inner对象  inner.print(300);//调用外部类的成员方法 }}

打印信息:

分析:观察上面的程序,你会发现三个number变量,其区别为:
number:引用的是print函数的形参;
this.number:引用的是Inner类中的成员变量;
Outer.this.number:引用的外部类Outer中的成员变量。
2.方法中定义的内部类
    嵌套类并非智能在类里定义,也可以在几个程序块的范围之内定义内部类。
源码:InnerDemo.java
//外部类class Outer{ private String str="姚明"; public void outerPrint() {    int i=10;    //内部类   class Inner   {    void dispaly(final int number)    {          System.out.println(str);     System.out.println(number);    //System.out.println(i);//这条语句是错误的,方法中的内部类不能访问方法的非final变量    }   }   //实例化内部类并调用其成员方法   Inner inner = new Inner();   inner.dispaly(11); }}public class InnerDemo{ public static void main(String[] args) {  Outer outer = new Outer();  outer.outerPrint(); }}

打印信息:

分析:在方法汇总定义的内部类智能访问方法中的final类型的局部变量(不能访问i),因为用final定义的局部变量就相当于一个常量,它的声明周期查处方法运行的生命周期。

二、匿名内部类
1.匿名类
    在学习匿名内部类之前,我们先看下这样一个实例,即实现一个内部类,该内部类继承于另外一个类,表述为在类Outer中定义一个内部类Inner,Inner类又继承了类A。
源码:Outer.java
//类Aabstract class A{ abstract void display();}//Outer类,在其main方法中定义一个内部类,该内部类继承于类Apublic class Outer { //main成员方法 public static void main(String[] args) {   //内部类   class Inner extends A   {    void display() {     System.out.println("I am Inner Class.");    }   }   new Outer().callInner(new Inner());//创建Outer实例并调用其成员方法,方法参数为内部类对象 } //callInner成员方法 public void callInner(A a) {  a.display(); }}
打印信息:

分析:由new Outer().callInner(new Inner());可知在Outer.main方法中调用了Outer.callInner方法,传递给callInner方法的参数要求是一个实现了类A中的方法的子类对象。所以,我们在Outer.main方法中定义了一个继承于A类的内部类Inner,该Inner类仅在这里被使用了一次。
    对于上面的程序感觉太复杂了,那么我们有什么办法简写它呢?当然。其实,我们在调用callInner方法时,不用实现定义类的Inner,可以在给callInner方法传递参数时,临时创建一个类A的匿名子类的实例对象,代码如下:
源码:Outer.java
//类Aabstract class A{ abstract void display();//声明一个抽象类}//外部类public class Outer { //main成员方法 public static void main(String[] args) {  new Outer().callInner(new A(){   void display() {    System.out.println("I am childclass of A,but I have not name -'Inner'");   }  }); } //callInner成员方法 public void callInner(A a) {  a.display(); }}
打印信息:

分析:  由程序打印的结果,我们可以看出Outer.main方法中调用了Outer.callInner方法,传递给callInner方法的参数要求是一个实现了类A中的方法的子类对象。在上面的程序中就相当于定义了一个类A的子类,但是这个子类是没有类名的,并且接着又创建了这个子类的一个实例对象,这样的类即为匿名类。
2.匿名类的形式
    假如我们实现实现了一个类A,那么它的匿名子类的一个实例对象可以这样表示。
形式:new A() { }
作用:产生一个类A的一个匿名子类的实例对象,匿名子类的所有实现代码(包括成员方法和成员变量)都要在那对大括弧间增加即可。

1 1
原创粉丝点击
热门问题 老师的惩罚 人脸识别 我在镇武司摸鱼那些年 重生之率土为王 我在大康的咸鱼生活 盘龙之生命进化 天生仙种 凡人之先天五行 春回大明朝 姑娘不必设防,我是瞎子 报到证上时间到期了还没报到怎么办 不停的打嗝已经超过24小时怎么办 面对不给下属做主的领导怎么办 法院说退款受伤人去不了证明怎么办 e栈快递柜没收到短信怎么办 京东快递放门卫丢了怎么办 丰巢快递柜收不到取件码怎么办 丰巢快递柜手机号码填错了怎么办 e栈手机号换了取不出来怎么办 买高铁票起点一样终点不一样怎么办 定火车票把名字写错一个字怎么办 火车票坐完车票丢了报销怎么办 客户交给我的钱被骗了怎么办 要证明网络来源的可靠性该怎么办 魅族手机高德地图信号弱怎么办 t恤的印花粘粘的怎么办 从包图网下载的模板素材丢失怎么办 大屏导航的语音功能怎么办用 手机导航不走地图上面走时怎么办 行车撞到步行人死亡师机逃离怎么办 小天才平板电脑不显示了怎么办 高德地图导航不显示车速怎么办 桥梁梁片强度达不到设计要求怎么办 新车交车检验表客户没签字怎么办 中铁快运职工拒绝提货要怎么办 奇瑞a3暖风水箱爆了怎么办 别人挖鱼塘占了我的山土怎么办 自己的鱼塘让别人强行占住了怎么办 公路扩路占地占了鱼塘怎么办? 玉米皮编垫子编好后玉米绳怎么办 入户门门框未预留纱窗位怎么办 门和墙有2cm缝隙怎么办 支座预埋钢板忘记埋了怎么办 做完线雕一边紧一边松怎么办 卖家把没发货的填写了单号怎么办 买的人民币白银亏了好多钱怎么办 带控制线的三相四线开关怎么办 覆膜除尘布袋风拉不动怎么办 家里装修把暖气管道打破了怎么办 冷水管与热水管接错了怎么办 磨砂皮的鞋子打湿变硬了怎么办