內部類訪問的局部變量必須加final

(1)內部類是外部類的一個成員,就像外部類的成員方法同樣,因此內部類有權限訪問外部類的全部成員,包括private的。 
(2)內部類不能訪問外部類方法中的局部變量,除非變量是final的(通常發生在方法中定義的內部類)。這是由於局部變量的生命週期緣由。  

 

  class Outer{    
  private int a;   
   public class Inner{   
       private int a;     
     public void method(int a){           
   a++;    //局部變量        
      this.a++;    //Inner類變量    
          Outer.this.a++;    //Outer類變量    
      }  
}
}    
 
 

 

通常作法是在Outer中寫一個返回Inner類對象的方法
  public Inner getInner(){   
   return new Inner(); 
 }    在其餘類中使用內部類:
  Outer outer = new Outer();  
Outer.Inner inner = outer.new Inner(); 或者 Outer.Inner inner = outer.getInner(); 
   static內部類的使用:  Outer.Inner inner = new Outer.Inner();  
 
  (1).所謂「局部內部類」就是在對象的方法成員內部定義的類。而方法中的類,訪問同一個方法中的局部變量,卻必需要加上一個final。
  (2).緣由是編譯程序實現上的困難:內部類對象的生命週期會超過局部變量的生命期。局部變量的生命期:當該方法被調用時,該方法中的局部變量在棧中被建立,當方法調用結束時,退棧,這些局部變量所有死亡。而內部類對象生命期,與其它類同樣,當建立一個局部內部類對象後,只有當沒有其它人再引用它時,它才能死亡。因此徹底可能一個方法已調用結束(局部變量已死亡),但該局部類的對象仍然活着。即:局部類的對象生命期會超過局部變量。
  (3).局部內部類的對象訪問同一個方法中的局部變量,那麼這就要求只要局部內部類對象還活着,那麼棧中的那些它要訪問的局部變量就不能「死亡」(不然:它都死了,還訪問個什麼呢?)。這就是說:局部變量的生命期至少等於或大於局部內部類對象的生命期。
  (4).解決方法:局部內部類的對象能夠訪問同一個方法中被定義爲final的局部變量。定義爲final後,編譯程序的實現方法:將全部的局部內部類對象要訪問的final型局部變量,都拷貝成爲該內部類對象中的一個數據成員。這樣,即便棧中局部變量(含final)已死亡,但因爲它是final,其值永不變,於是局部內部類對象在變量死亡後,照樣能夠訪問final型局部變量。(這一點我有些懷疑)
  (5).概括總結:局部內部類對象中包含有要訪問的final型局部變量的一個拷貝,成爲它的數據成員。所以,正是在這個意義上,final型局部變量的生命期,超過其方法的一次調用。嚴格來講,方法調用結束,全部的局部變量(含final)全死亡了。但:局部內部類對象中有final型局部變量的拷貝。
final 補充說明:
  1.在java中聲明類、屬性、方法時,可以使用關鍵字final來修飾
  2.final標記的類不能被繼承。
  3.final標記的方法不能被子類重寫 
 4.final標記的變量(成員變量或局部變量)即成爲常量,只能賦值一次。  
5.final標記的變量必須在聲明的同時或在構造方法中顯示賦值,而後才能使用。   
 final int x = 5;
  class Test{     
 final int x ; 
     Test(){    
      x=3;   
  }  }
相關文章
相關標籤/搜索