標籤:style blog http io ar color os 使用 sp
VS2015預覽版中的C#6.0 新功能(一)
VS2015預覽版中的C#6.0 新功能(三)
自動屬性的增強
以前自動屬性必須同時提供setter和getter方法,因而唯讀屬性只能通過先聲明field,然後property只提供getter方法來實現,無法通過自動屬性來實現。在c#6.0中,可以通過如下的形式聲明唯讀自動屬性:
public string FirstName { get; }
對於唯讀自動屬性,其backing field是readonly的,其值可以在屬性初始化器(下面會詳細講解屬性初始化器)或者類的建構函式中給予。在下面的例子中FirstName和LastName屬性是通過自動屬性初始化器賦值的,而TimeOfStartingWrite是通過建構函式賦值的。
public class Author{ public DateTime TimeOfStartingWrite { get; } public string FirstName { get; } = "Dery"; public string LastName { get; } = "Xu"; public Author(DateTime timeOfStartingWrite) { TimeOfStartingWrite = timeOfStartingWrite; }}
由於唯讀屬性沒有setter方法,它的值是通過直接賦給其backing field的。
在上面的例子中可以看到對於自動屬性,我們可以使用屬性初始化器來為其賦值。例子如下:
public class Book { public int Number { get;}=100; public string Abstract { get; set; }="this is abstract"; public string Name { get; set; } public float Price { get; set; } public Author PrimaryAuthor { get; set; } public List<Author> Authors { get; set; } }
其中Number是一個唯讀自動屬性,我們通過屬性初始化器為其賦值100,而Abstract是一個可讀寫的自動屬性,我們通過屬性初始化器為其賦值為字串"this is abstract"。自動屬性初始化器直接賦值給後台產生的field,不會走自動屬性的setter方法。它和field初始化器一樣具有如下的一些特點:
- 按照書寫順序執行,所以在上例中,先執行Number屬性的初始化,再執行Abstract屬性的初始化
- 不能使用this,因為它是在對象完全初始化之前啟動並執行
自動屬性初始化器中可用來賦給屬性的值似乎很有限,而下面的主建構函式可以協助它獲得跟多可能的值。
主建構函式
主建構函式功能把建構函式的聲明合并到了類的聲明中。讓我們可以編寫如下所示的代碼:
[Serializable]public class Patent(string title, string yearOfPublication){ public Patent(string title, string yearOfPublication, IEnumerable<string> inventors) :this(title, yearOfPublication) { Inventors.AddRange(inventors); } private string _Title = title; public string Title { get { return _Title; } set { if (value == null) { throw new ArgumentNullException("Title"); } _Title = value; } }}
然而,這次的release中還不支援該功能,會在以後的更新中進一步說明。
運算式體函數和屬性
對於Lambda運算式,我們知道可以通過運算式體或者在語句塊中的普通函數來聲明,現在這個功能也可以應用到類的函數成員上。
public int Add(int op1, int op2) => op1 + op2; public void Print(string message) => Console.WriteLine("Hello " + message);
使用運算式體函數的效果和只有單一return語句的函數體一樣,所以上面的例子和下面的code是一樣的
public int Add(int op1, int op2){ return op1 + op2;}public void Print(string message){ Console.WriteLine("Hello " + message);}
請注意Add方法是有傳回值的,而Print是沒有傳回值的,對於沒有傳回值的函數,Lambda運算式體必須是語句Lambda即new, call, decrement,increment,賦值等表達完整語句的操作而非運算式,這個要求和lambda是一樣的。
屬性和索引器有getter和setter方法,運算式體可以用來寫唯讀屬性和索引器,運算式體就是對應getter方法的方法體,例子如下:
public Author this[int id] => store[id];public string FullName => firstName + lastName;
注意這裡不需要給出get關鍵字,編譯器會做隱式推斷。
完整例子如下
internal class ExpressionBody { private string firstName = "first name"; private string lastName = "lastName"; private List<Author> store = new List<Author> { new Author(DateTime.Now), new Author(DateTime.Now) }; public int Add(int op1, int op2) => op1 + op2; public void Print(string message) => Console.WriteLine("Hello " + message); public Author this[int id] => store[id]; public string FullName => firstName + lastName; //public int Add(int op1, int op2) //{ // return op1 + op2; //} //public void Print(string message) //{ // Console.WriteLine("Hello " + message); //} }
VS2015預覽版中的C#6.0 新功能(二)