方法中的內部類不能訪問該方法的局部變量

1)所謂「局部內部類」就是在對象的方法成員內部定義的類。而方法中的類,訪問同一個方法中的局部變量,是天經地義的。那麼爲何要加上一個final呢? spa

2)緣由是:編譯程序實現上的困難,難在何處:內部類對象的生命週期會超過局部變量的生命期。爲何?表如今:局部變量的生命期:當該方法被調用時,該方法中的局部變量在棧中被建立(誕生),當方法調用結束時(執行完畢),退棧,這些局部變量所有死亡。而:內部類對象生命期,與其它類同樣,當建立一個該局部類對象後,只有沒有其它人再引用它時,它才能死亡。徹底可能:一個方法已調用結束(局部變量已死亡),但該局部類的對象仍然活着。即:局部類的對象生命期會超過局部變量。 對象

3)退一萬步:局部類的對象生命期會超過局部變量又怎樣?問題的真正核心是:若是:局部內部類的對象訪問同一個方法中的局部變量,是天經地義的,那麼:只要局部內部類對象還活着,則:棧中的那些它要訪問的局部變量就不能「死亡」(不然:它都死了,還訪問個什麼呢?),這就是說:局部變量的生命期至少等於或大於局部內部類對象的生命期。而:正是這一點是不可能作到的 接口

4)可是從理論上:局部內部類的對象訪問同一個方法中的局部變量,是天經地義的。因此:通過努力,達到一個折中結果:即:局部內部類的對象能夠訪問同一個方法中的局部變量,只要這個變量被定義爲final.那麼:爲何定義爲final變能夠呢?定義爲final後,編譯程序就好實現了:具體實現方法是:將全部的局部內部類對象要訪問的final型局部變量,變成該內部類對象中的一個數據成員。這樣,即便棧中局部變量(含final)已死亡,但因爲它是final,其值永不變,於是局部內部類對象在變量死亡後,照樣能夠訪問final型局部變量。生命週期

概括上述回答的真正核心是:局部內部類對象中包含有要訪問的final型局部變量的一個拷貝,成爲它的數據成員。所以,正是在這個意義上,final型局部變量的生命期,超過其方法的一次調用。嚴格來講,方法調用結束,全部的局部變量(含final)全死亡了。但:局部內部類對象中有final型局部變量的拷貝。內存

其餘:編譯

無論對象是否是final,他的生命週期都是 new開始,垃圾回收結束。 class

無論變量是否是final,他的生命週期都在於{}中。 變量

類對象(class對象)與其它對象不一樣,類對象的生命週期 開始於類被加到內存中那一刻,結束於垃圾回收。 垃圾回收

類變量(static)與類對象的生命週期相同。引用

public class LocalInnerClassTest{  

      public static void main(String[] args){  

         Outer obj=new Outer();          //生成一個外部類對象  

         SuperInner si=obj.outer();        //調用外部類中的outer()方法,返回一個SuperInner類型對象賦值給si  

        si.m1();             //調用被覆蓋的方法m1(),輸出:Inner's m1() 20  

     }  

}  

/** 

*定義一個接口SuperInner,內部定義一個抽象方法m1(),無返回類型 

*/  

interface SuperInner{  

     public void m1();  

}  

/** 

*定義一個類Outer,內部只定義一個方法outer(),返回類型爲SuperInner 

*/  

class Outer{  

     public SuperInner outer(){  

        int a=10;                   //方法中定義一個局部變量a,並賦值爲10  

        final int b=20;          //再定義一個final局部變量b,初始化爲20  

  

        class Inner implements SuperInner{              //在outer()方法中定義一個局部內部類Inner,實現接口SuperInner  

           public void m1(){    //類中只有一個覆蓋接口SuperInner的方法m1()  

              System.out.println("Inner's m1()"+a);    //編譯報錯  

              System.out.println("Inner's m1() "+b);    //編譯經過,輸出:Inner's m1() 20  

           }  

        }  

        return new Inner();  

     }  

}  

相關文章
相關標籤/搜索