天天看點

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

關于JAVA匿名内部類的一點讨論.

基本理論:

-----------------------------------------------------

關于JAVA内部類:一個内部類的定義是定義在另一個類内部的類。

  存在它的原因是:

  1.一個内部類的對象能夠通路建立它的對象的實作,包括私有資料。即内部類執行個體對包含它的哪個類的執行個體來說,是特權的。

  2.對于同一個包中的其他類來說,内部類能夠隐藏起來,換句話說,内部類不管方法的可見性如何,那怕是public,除了包容類,其他類都無法使用它。

  3.匿名内部類可以很友善的定義回調。

  4.使用内部類可以非常友善的編寫事件驅動程式。

其實它真正的目的僅僅為了定義回調--進一步就是事件驅動。

接口和回調:程式設計一個常用的模式是回調模式,在這種模式中你可以指定當一個特定時間發生時回調對象上的方法。

--------------------------------------------------

 注意事項:

 匿名類和内部類中的中的this :

 有時候,我們會用到一些内部類和匿名類。當在匿名類中用this時,這個this則指的是匿名類或内部類本身。

 這時如果我們要使用外部類的方法和變量的話,則應該加上外部類的類名。如下面這個例子:

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

public class A {

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

  int i = 1;

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

  public A() {

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

    Thread thread = new Thread() {

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

      public void run() {

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

        for(;;) {

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

          A.this.run();

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

          try {

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

            sleep(1000);

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

          } catch(InterruptedException ie) {

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

          }

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

        }

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

      }

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

    };

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

    thread.start();

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

  }  

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

  public void run() {

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

    System.out.println("i = " + i);

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

    i++;

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

  }

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

  public static void main(String[] args) throws Exception {

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

    new A();

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

}

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

    在上面這個例子中, thread 是一個匿名類對象,在它的定義中,它的 run 函數裡用到了外部類的 run 函數。

    這時由于函數同名,直接調用就不行了。這時有兩種辦法,一種就是把外部的 run 函數換一個名字,但這種辦法對于一個開發到中途的應用來說是不可取的

    。那麼就可以用這個例子中的辦法用外部類的類名加上 this 引用來說明要調用的是外部類的方法 run。

    --------------------------------------------------

    對于這個例子:

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

this.test(new Inner(){

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

             public void method1(){

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

                 System.out.print("1111");

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

           }

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

             public void method2(){

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

                 System.out.print("22222");

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

});

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

這個時候調用test()方法,那Inner類的method1和method2是什麼時候被調用的?難道也是this對象向他們發消息(比如傳入一個參數)嗎?還是直接顯式的調用??

對于Inner類,除了this這個類,就是this.test(...那句中的this,它能夠調用Inner類的方法,其他地方都不行,然而,這也需要你在類中有個地方儲存有對這個内部類執行個體的引用才可以。再說明一次,内部類是用來在某個時刻調用外面的方法而存在的--這就是回調。

為了說明内部類執行個體的方法隻能在包容類的執行個體中調用,其他地方無法調用,給個例子如下:

JAVA2實用教程源碼:

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

 /** 一個應用程式,用來示範内部類的使用 */

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

/** 類Outer */

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

class Outer{ 

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

private static int size;

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

/** 内部類Inner的聲明 */

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

public class Inner{ 

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

private int size;

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

/** 方法doStuff() */

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

public void doStuff(int size){ 

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

size++; //存取局部變量

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

this.size++;  //存取其内部類的成員變量

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

Outer.this.size++; //存取其外部類的成員變量

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

System.out.println(size+" "+this.size+" "+Outer.this.size);

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

}//内部類Inner結束

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

/** 類Outer中定義的執行個體方法testInner()方法 */

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

public void testInner(){

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

Inner i=new Inner();

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

i.doStuff(5); 

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

/** main()方法 */

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

public static void main(String[] a){ 

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

Outer o=new Outer();

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

o.testInner();

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

}//類Outer結束

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

------------------------------------------------

那麼,如何使用内部類,匿名類實作事件處理呢?

JAVA---事件擴充卡

 1.事件擴充卡--EventAdapter

  下例中采用了滑鼠擴充卡:

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

import java.awt.*;

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

  import java.awt.event.*;

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

  public class MouseClickHandler extends MouseAdaper{

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

    public void mouseClicked(MouseEvent e) //隻實作需要的方法

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

       { ……}

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

  } 

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

  java.awt.event包中定義的事件擴充卡類包括以下幾個:

1.ComponentAdapter( 元件擴充卡) 

2.ContainerAdapter( 容器擴充卡) 

3.FocusAdapter( 焦點擴充卡) 

4.KeyAdapter( 鍵盤擴充卡) 

5.MouseAdapter( 滑鼠擴充卡) 

6.MouseMotionAdapter( 滑鼠運動擴充卡)

7.WindowAdapter( 視窗擴充卡)

 2. 用内部類實作事件處理

  内部類(inner class)是被定義于另一個類中的類,使用内部類的主要原因是由于:

◇ 一個内部類的對象可通路外部類的成員方法和變量,包括私有的成員。

◇ 實作事件監聽器時,采用内部類、匿名類程式設計非常容易實作其功能。

◇ 編寫事件驅動程式,内部類很友善。  

是以内部類所能夠應用的地方往往是在AWT的事件處理機制中。

例5.11

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

import java.awt.* ;

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

   import java.awt.event.*;

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

     public class InnerClass{

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

       private Frame f;

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

       private TextField tf;

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

       public InnerClass(){

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

       f=new Frame("Inner classes example");

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

       tf=new TextField(30);

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

     }

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

     public voidi launchFrame(){

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

       Label label=new Label("Click and drag the mouse");

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

       f.add(label,BorderLayout.NORTH);

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

       f.add(tf,BorderLayout.SOUTH);

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

       f.addMouseMotionListener(new MyMouseMotionListener());/*參數為内部類對象*/

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

       f.setSize(300,200);

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

       f.setVisible(true); 

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

     class MyMouseMotionListener extends MouseMotionAdapter{ /*内部類開始*/

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

       public void mouseDragged(MouseEvent e) {

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

         String s="Mouse dragging: x="+e.getX()+"Y="+e.getY();

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

         tf.setText(s); }

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

       } ;

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

       public static void main(String args[]) {

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

         InnerClass obj=new InnerClass();

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

         obj.launchFrame();

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

       }

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

     }//内部類結束

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

    }

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

 3.匿名類(Anonymous Class)

  當一個内部類的類聲名隻是在建立此類對象時用了一次,而且要産生的新類需繼承于一個已有的父類或實作一個接口,才能考慮用匿名類,由于匿名類本身無名,是以它也就不存在構造方法,它需要顯示地調用一個無參的父

類的構造方法,并且重寫父類的方法。所謂的匿名就是該類連名字都沒有,隻是顯示地調用一個無參的父類的構造方法。

例5.12

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

   import java.awt.event.*;

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

    public class AnonymousClass{

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

     private Frame f;

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

     private TextField tf;

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

     public AnonymousClass(){

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

      f=new Frame("Inner classes example");

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

      tf=new TextField(30);

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

    public void launchFrame(){

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

      Label label=new Label("Click and drag the mouse");

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

      f.add(label,BorderLayout.NORTH);

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

      f.add(tf,BorderLayout.SOUTH);

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

      f.addMouseMotionListener(new MouseMotionAdapter(){ //匿名類開始

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

       public void mouseDragged(MouseEvent e){

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

        String s="Mouse dragging: x="+e.getX()+"Y="+e.getY();

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

        tf.setText(s); }

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

      } ); //匿名類結束 

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

      f.setSize(300,200);

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

      f.setVisible(true);

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

      }

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

        AnonymousClass obj=new AnonymousClass();

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

        obj.launchFrame();

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

        }

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式
關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

  其實仔細分析,例5.11和5.12實作的都是完全一樣的功能,隻不過采取的方式不同。5.11中的事件處理類是一個内部類,而5.12的事件處理類是匿名類,可以說從類的關系來說是越來越不清楚,但

是程式也越來越簡練。熟悉這兩種方式也十分有助于編寫圖形界面的程式。

親自在IDE中實踐一下,會了解的更深切一點。

然而,在.NET中實作事件模式,就要簡單的多,這樣的文章很多,不過也不妨繼續讨論讨論。

關于JAVA匿名内部類,回調,事件模式的一點讨論 VS dotNET事件模式

本文轉自斯克迪亞部落格園部落格,原文連結:http://www.cnblogs.com/sgsoft/archive/2004/09/11/42148.html如需轉載請自行聯系原作者