你知道屬性(字段)與構造函數誰先執行嗎?
最近一直在馬不停蹄的做開發,正所謂學而不思則罔,思而不學則殆,開發過程中其實學到了好多,也發現了好多,但是有時候會因為某些原因沒能深入探討和研究,而只是想當然的處理,今天突然閑心泛濫,想研究下一個類中屬性與構造函數到底哪個先執行,執行順序策略是怎樣的?這個問題其實已經困擾我好久,因為有些整個類中需要使用的一下對象,我有時候喜歡直接在聲明的時候就進行實例化,但是這樣真的好嗎?會不會影響到速度、性能之類的問題?我看過一些別人的代碼,總之,有的將實例化對象放到構造函數中,有的直接實例化,今天就來測試一下它的執行順序。
真是不看不知道,一看嚇一跳,編程的偉大油然而生,現在按照這樣的順序來敘述本篇文章:為什么要測試---要測試什么---怎么測試---開始測試---別人的看法---結論(溫馨提示,結論不一定是真理)。
既然測試,那就測試全一點,首先測試實例化與未實例化屬性和構造函數的執行順序,測試未初始化與初始化的屬性和構造函數的執行順序,測試構造函數和未初始化與初始化的屬性的執行順序,測試構造函數和初始化與未初始化的屬性的執行順序,測試構造函數和初始化與未初始化的屬性的執行順序。
將上述需要測試的地方全部用代碼實現,如下:
1 public class SportJudge 2 { 3 private DAL.SportJudgeDataContext sj = new DAL.SportJudgeDataContext(); 4 /*先測試初始化與未初始化的屬性和構造函數的執行順序*/ 5 private String test1; //沒有初始化 6 private String test2 = "我被初始化了..."; //初始化 7 /*先測試初始化與未初始化的屬性和構造函數的執行順序*/ 8 9 10 /*測試未初始化與初始化的屬性和構造函數的執行順序*/ 11 private String test3 = "我被初始化了..."; //初始化 12 private String test4; 13 /*測試未初始化與初始化的屬性和構造函數的執行順序*/ 14 //默認構造函數 15 public SportJudge() 16 { 17 test8 = "我在構造函數中被初始化了"; 18 } 19 /*測試構造函數和未初始化與初始化的屬性的執行順序*/ 20 private String test5; 21 private String test6 = "我被初始化了..."; 22 /*測試構造函數和未初始化與初始化的屬性的執行順序*/ 23 24 /*測試構造函數和初始化與未初始化的屬性的執行順序*/ 25 private String test7 = "我被初始化了..."; 26 private String test8; 27 /*測試構造函數和初始化與未初始化的屬性的執行順序*/ 28 }
將每句話都加上斷點,構造函數加一個斷點就行了,然后開始debug,神奇的事情出現了,所有未實例化的屬性全部沒有被執行,直接無法對未實例化的屬性進行debug,然后其他的執行順序如下:
網上有人說執行順序一定是構造函數先執行,字段在后面才執行,當然也有說不知道的,總之能正常執行就行了,管他呢。
基本結論如下:如果字段沒有賦值,則直接跳過,若有賦值,則優先於構造函數執行初始化,不管該字段在構造函數前邊還是后邊。如果有多個字段都有賦值,那么按照代碼從上到下依次執行,所有的字段處理完畢后再執行構造函數。最后想想這樣的執行順序也算是合乎情理,所謂巧婦難為無米之炊嘛,字段就相當於菜、米和調料,是基礎的資源,構造函數就像是一個鍋,而方法則是各種烹飪技術。此種比喻僅為個人看法,算了,我承認我餓了...
趁熱打鐵,我打開eclipse集成環境,迅速用java編寫同樣的代碼,如下:
1 public class Test { 2 /*先測試初始化與未初始化的屬性和構造函數的執行順序*/ 3 private String test1; //沒有初始化 4 private String test2 = "我被初始化了..."; //初始化 5 /*先測試初始化與未初始化的屬性和構造函數的執行順序*/ 6 7 8 /*測試未初始化與初始化的屬性和構造函數的執行順序*/ 9 private String test3 = "我被初始化了..."; //初始化 10 private String test4; 11 /*測試未初始化與初始化的屬性和構造函數的執行順序*/ 12 public Test(){ 13 String test11 = "我是構造函數"; 14 } 15 /*測試構造函數和未初始化與初始化的屬性的執行順序*/ 16 private String test5; 17 private String test6 = "我被初始化了..."; 18 /*測試構造函數和未初始化與初始化的屬性的執行順序*/ 19 20 21 /*測試構造函數和初始化與未初始化的屬性的執行順序*/ 22 private String test7 = "我被初始化了..."; 23 private String test8; 24 /*測試構造函數和初始化與未初始化的屬性的執行順序*/ 25 public static void main(String[] args) { 26 Test t = new Test(); 27 } 28 }
作者:楊浩瑞
時間:2015年05月22日