微軟計畫 C# 8.0 與 .NET Core 3.0 同一時間發布,應該是跟隨 Visual Studio 2019 一起上線吧。
Nullable reference types
本來的可空類型是經由 System.Nullable
int? a = null;
string? s = null; // 編譯錯誤
而現在連 reference types 也可以當作可空類型,如
void Method (string? s) {
if (s != null) {
Console.WriteLine(s.Length); //不為 null 才能使用成員
}
}
可以取代空字串的使用。
小提一下個人理解,null 是不指向任何值;string.Empty 是指向一個 String 的靜態屬性;”” 是建立一個字串並給予空值。
而這邊有個問題,不知道是哪邊出問題 string s = null 並不會像官方範例一樣跳出警告。
Async streams
IAsyncEnumerable
async IAsyncEnumerable<int> GetBigResultsAsync () {
await foreach (var result in GetResultsAsync ()) {
if (result > 20) yield return result;
}
}
等正式上線再來實作看看。
Ranges and indices
新的類型 Index,可以用於集合的查找上,如
Index i1 = 3; // number 3 from beginning
Index i2 = ^4; // number 4 from end
int[] a = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 };
Console.WriteLine($"{a[i1]}, {a[i2]}"); // "3, 6"
也可以當作範圍使用,如
var slice = a[i1..i2]; // { 3, 4, 5 }
Default implementations of interface members
介面成員增加預設實作的成員。
改善介面發布後,若介面有新增成員,實作該介面的類別不再強制需要補寫新成員,有一個預設實作成員,如果需要改變才另寫實作。
interface ILogger {
void Log (LogLevel level, string message);
void Log (Exception ex) => Log (LogLevel.Error, ex.ToString ()); // New overload
}
class ConsoleLogger : ILogger {
public void Log (LogLevel level, string message) { ... }
// Log(Exception) gets default implementation
}
Recursive patterns
允許新寫法如
IEnumerable<string> GetEnrollees () {
foreach (var p in People) {
if (p is Student { Graduated: false, Name: string name }) yield return name;
}
}
個人猜類似於
IEnumerable<string> GetEnrollees () {
foreach (var p in People) {
if (p is Student && p.Graduated == false && p.Name is string) yield return p.name;
}
}
Switch expressions
Switch 的表達式
var area = figure switch
{
Line _ => 0,
Rectangle r => r.Width * r.Height,
Circle c => Math.PI * c.Radius * c.Radius,
_ => throw new UnknownFigureException (figure)
};
個人猜類似於以下陳述式
var area = 0;
switch (figure) {
case Line _:
area = 0;
break;
case Rectangle r:
area = r.Width * r.Height;
break;
case Circle c:
area = Math.PI * c.Radius * c.Radius;
break;
default:
throw new UnknownFigureException (figure);
break;
}
switch 的陳述式更新可以參考 C# 7.0 的新功能 - C# 指南 | Microsoft Docs
Target-typed new-expressions
當上下文可以推導出類型時,可以省略類型。
Point[] ps = { new (1, 4), new (3,-2), new (9, 5)};
個人猜類似於
Point[] ps = { new Point (1, 4), new Point (3,-2), new Point (9, 5)};
總結
官方的文章還有提到平台的依賴,但應該不用特別注意,大多數的平台都可以運行,除了 .NET Framework 4.8 版本不能使用 Async streams 與 Default interface member implementations 特性。
雖然我記得還有一些新特性,但可能不是官方正式文件所以不在這次的改版內容裡。
參考資料
Building C# 8.0 | .NET Blog
C# - 維基百科,自由的百科全書
Nullable<T> Struct (System) | Microsoft Docs