2014-08-29 49 views
5

首先之前,這個問題具有着與這些漂亮的問題:通過getter訪問最後一個字段的初始化

1)Use of uninitialized final field - with/without 'this.' qualifier

2)Why isn't a qualified static final variable allowed in a static initialization block?

但我會問它另一個角度來看。只是要記住:上述提到的問題被詢問關於使用關鍵字thisJava 7中訪問final字段。

在我的問題中有類似的東西,但不一樣。那麼,考慮下面的代碼:

public class TestInit { 
    final int a; 
    { 
     // System.out.println(a); -- compile error 
     System.out.println(getA()); 
     // a = a;     -- compile error 
     a = getA(); 
     System.out.println(getA()); 
    } 
    private int getA() { 
     return a; 
    } 
    public static void main(String[] args) { 
     new TestInit(); 
    } 
} 

和輸出是:

0 
0 

正如你可以看到這裏有兩個不清楚的事情:

  1. 沒有訪問非另一種合法的方式初始化的final字段:使用它的getter。
  2. 我們應該考慮的是空白決賽場上,它的分配新建分配FY a = getA();法律將始終分配給它的默認值一樣,根據JLSfinal場?換句話說,它是否應該被視爲預期的行爲?
+0

您鏈接的問題具有JLS規定的規則。他們沒有說任何關於調用方法的東西,所以這些都是允許的。 – 2014-08-29 18:46:32

回答

0

你真正遇到的是編譯器的推理能力。 對於您的第一個編譯器錯誤,由於編譯器肯定知道未分配,所以失敗。與第二個a = a相同(不能從a進行賦值,因爲它絕對沒有在此處指定)。 工作a = getA()的行是a的第一個單一明確賦值,所以這很好(不管值從何而來; getA()的實現無關緊要,並且此時不進行評估)。

getA()方法是有效的,並且可以返回一個值,因爲實例初始值設定項已明確賦值給a。

對於一個看着它的人​​來說它是有道理的,但它並不是編譯器內置的推理。每個獨立評估的塊都是有效的。

+0

哪個「靜態初始化器」?對不起,你在說什麼? – Andremoniy 2014-08-29 17:27:06

+0

對不起,實例初始值設定項(我已編輯更正)。 – user1676075 2014-08-29 18:38:46