一. 語法糖簡介html
語法糖也譯爲糖衣語法,是由英國計算機科學家彼得·約翰·蘭達(Peter J. Landin)發明的一個術語,指計算機語言中添加的某種語法,這種語法對語言的功能並無影響,可是更方便程序員使用。一般來講使用語法糖可以增長程序的可讀性,從而減小程序代碼出錯的機會。程序員
須要聲明的是「語法糖」這個詞絕非貶義詞,它能夠給我帶來方便,是一種便捷的寫法,編譯器會幫咱們作轉換;並且能夠提升開發編碼的效率,在性能上也不會帶來損失。編程
在編譯器發展早期,編譯器科學家門一直在千方百計的優化編譯器生成的代碼,這個時候,編譯器作的主要是對機器優化,由於那個時候機器的時間很是寶貴,機器運算速度也不快,今天咱們有了足夠好的機器了(但並非說咱們能夠不關注性能的編寫程序),並且做爲編寫軟件的人來講,比機器的時間寶貴得多,因此今天的編譯器也在向人優化了,從編程語言的發展之路來說,今天的編程語言比昨天的語言更高級,也更人性化了,咱們只要編寫更少的代碼,更符合人的思惟的代碼,而只要關注咱們值的關注的地方。體力活兒就交給編譯器吧。編程語言
二. 經常使用語法糖性能
1. 自動屬性優化
(1). 傳統的方式在類中聲明一個屬性,須要先聲明一個私有變量的字段,而後在配合公有屬性,以下面的:userId屬性。編碼
(2). 利用自動屬性:不須要字段,聲明一個空屬性,直接get,set(快捷鍵:prop),編譯時編譯器爲咱們生成存取數據的字段. 以下面的:userName屬性。spa
1 public class userInfor 2 { 3 //私有字段 4 private string _userId; 5 //公有屬性 6 public string userId 7 { 8 get 9 { 10 return _userId; 11 } 12 set 13 { 14 _userId = value; 15 } 16 } 17 18 public string useName { get; set; } 19 20 21 /// <summary> 22 /// 爲了後面的反射調用 23 /// </summary> 24 public void Test() 25 { 26 Console.WriteLine("我是一個方法"); 27 } 28 29 }
2. var和dynamiccode
(1). var類型:聲明變量的時候能夠不指定類型,由編譯器編譯的時候來指定類型。htm
①:必須在定義的時候初始化
②:必須是局部變量
③:一旦初始化完成,不能再給變量賦與初始值不一樣類型的值了,可是能夠賦相同類型的不一樣值.
④:var在效率是和使用強類型方式定義變量是同樣的
(2). dynamic類型:編譯期間不作任何檢查,運行期間才肯定類型。
①:定義的時候能夠沒必要初始化
②:能夠是全局變量,也能夠是局部變量
dynamic在反射中的應用:經過反射拿到類後,賦值給dynamic類型,該類型的對象能夠直接點來調用方法
缺點:dynamic在運行的時候才進行檢測,致使編譯的時候即便有錯誤也不會被發現; 不能用dynamic類型給肯定類型的變量進行賦值
1 public class CompareTwo 2 { 3 //2. 可以使用的範圍 4 // var b1 = 1; //報錯,var必須定義在方法呃逆 5 // dynamic b2 = 2; //正常 6 public static void Show() 7 { 8 { 9 //1. 初始化比較 10 //var a1; //報錯,定義的時候必須初始化 11 //dynamic a2; //正常 12 } 13 { 14 //3. 賦值問題 15 var c1 = 2; 16 //c1 = "2"; //報錯,初始化完成不能賦值不一樣類型的變量 17 c1 = 3; //正常,初始化完成能夠賦值相同類型的變量的不一樣值 18 19 dynamic d1 = 2; 20 d1 = "2"; //正常,運行時檢查進行類型指定,因此在編譯的時候不會報錯 21 d1 = 3; //正常 22 23 24 var userInfor = new userInfor(); 25 userInfor.useName = "1"; 26 userInfor.userId = "2"; 27 // userInfor.fk123(); //報錯,編譯不經過 28 29 dynamic userInfor2 = new userInfor(); 30 userInfor2.userId = "1"; 31 userInfor2.useName = "ypf"; 32 //調用不存在的方法 (由於編譯的時候根本不檢查,因此不會報錯,運行的時候報錯) 33 //userInfor2.fk123(); //編譯期間不報錯,運行的時候報錯 34 35 } 36 { 37 //4. dynamic在反射中的應用 38 //4.1 常規反射調用方法 39 Type type1 = typeof(userInfor); 40 object oStudent = Activator.CreateInstance(type1); 41 MethodInfo method = type1.GetMethod("Test"); 42 method.Invoke(oStudent,null); 43 44 //4.2 利用dynamic簡化調用 45 //定義和編譯的時候能夠是任何類型,運行的時候進行轉換 46 dynamic oStudent2 = Activator.CreateInstance(type1); 47 oStudent2.Test(); 48 49 } 50 } 51 }
3. 可選參數
給方法的參數能夠指定默認值,若是在調用該方法的時候,不傳入該參數,則走默認值,傳入的話,則覆蓋默認參數.
(1). 有默認值的參數必須定義在沒有默認值的參數以後
(2). 默認參數必須是常量,不能是變量
(3). ref和out參數不能指定默認值
1 public class OptionalParas 2 { 3 public static void Test(string useName,string userPwd,int userAge=16,string userSex="男") 4 { 5 Console.WriteLine("userName:{0},userPwd:{1},userAge:{2},userSex:{3}", useName, userPwd, userAge, userSex); 6 } 7 }
1 //3.可選參數 2 Console.WriteLine("----------------------3.可選參數-------------------------"); 3 OptionalParas.Test("ypf1", "123456"); 4 OptionalParas.Test("ypf2", "654321", 56, "女");
4. 對象(集合)初始化器
1 public class ObjectInitilize 2 { 3 public static void Test() 4 { 5 6 //一.對象初始化 7 //1. 傳統初始化對象的方式 8 userInfor uInfor1 = new userInfor(); 9 uInfor1.userId = "1"; 10 uInfor1.useName = "ypf1"; 11 12 //2.對象初始化器 13 userInfor uInfor2 = new userInfor() 14 { 15 userId="2", 16 useName="ypf2" 17 }; 18 userInfor uInfor3 = new userInfor() 19 { 20 userId = "3", 21 useName = "ypf3" 22 }; 23 24 //二. 集合初始化 25 //1. 傳統方式 26 List<userInfor> uList = new List<userInfor>(); 27 uList.Add(uInfor1); 28 uList.Add(uInfor2); 29 30 //2. 集合初始化器 31 List<userInfor> uList2 = new List<userInfor>(){ 32 uInfor1, 33 uInfor2, 34 new userInfor(){ 35 userId="4", 36 useName="ypf4" 37 } 38 }; 39 40 } 41 }
5. ref和out
兩者共同的使用場景,將ref或out參數傳入方法中,執行完方法後,能夠直接使用ref或out參數值。
(1). ref必須在使用前賦值,即傳入方法前進行定義並賦值
(2). out必須在方法中賦值而後使用,在調用方法前聲明兩個未實例化的變量,用來傳入和接收使用
舉例:有兩個int類型的值num1和num2,分別使用ref和out傳入對應的方法中,進行值交換。
1 public class CompareRO 2 { 3 /// <summary> 4 /// ref的使用 5 /// </summary> 6 public static void TestRef() 7 { 8 int num1 = 5; 9 int num2 = 10; 10 Func1(ref num1, ref num2); 11 Console.WriteLine("num1的值爲:{0},num2的值爲:{1}", num1, num2); 12 } 13 14 public static void TestOut() 15 { 16 int num1; 17 int num2; 18 Func2(out num1, out num2); 19 Console.WriteLine("num1的值爲:{0},num2的值爲:{1}", num1, num2); 20 } 21 22 #region ref版參數值交換 23 public static void Func1(ref int n1, ref int n2) 24 { 25 int a = n1; 26 n1 = n2; 27 n2 = a; 28 } 29 #endregion 30 31 #region out版參數值交換 32 public static void Func2(out int n1,out int n2) 33 { 34 n1 = 5; 35 n2 = 10; 36 int a = n1; 37 n1 = n2; 38 n2 = a; 39 } 40 #endregion 41 42 }
6. 匿名類/匿名方法
7. 擴展方法