.NET 6 预览版 7 发布--(最后一个预览版)
原文:bit.ly/2VJxjxQ
作者:Richard
翻譯:精致碼農(nóng)-王亮
說明:文中有大量的超鏈接,這些鏈接在公眾號文章中被自動剔除,一部分包含超鏈接列表的小段落被我刪減了,如果你對此感興趣,請參考閱讀原文。
我們很高興地發(fā)布了 .NET 6 預(yù)覽版 7。這是我們進(jìn)入(兩個)候選發(fā)布版(RC)之前的最后一個預(yù)覽版。在我們放慢發(fā)布速度之前,團(tuán)隊一直在螢窗雪案,以完成最后一組功能。在這個版本中,你將看到各功能的最后一次拋光,一次到位地整合整個版本的大型功能。從此時起,團(tuán)隊將專注于使所有的功能達(dá)到統(tǒng)一的(高)質(zhì)量,以便 .NET 6 為你的生產(chǎn)工作做好準(zhǔn)備。
關(guān)于生產(chǎn)工作的話題,值得提醒大家的是,.NET 官網(wǎng)[1]和 Bing.com 從預(yù)覽版 1 開始就一直運行在 .NET 6 上。我們正在與不同的團(tuán)隊(微軟和其他公司)商談有關(guān)進(jìn)入生產(chǎn)的 .NET 6 RC 版本。如果你對此感興趣,并希望得到相關(guān)的指導(dǎo),請聯(lián)系 dotnet@microsoft.com。我們始終很樂意與早期采用者交流。
你可以在這下載[2] Linux、macOS 和 Windows 的 .NET 6 預(yù)覽版 7。
- 安裝程序和二進(jìn)制文件https://dotnet.microsoft.com/download/dotnet/6.0 - 容器鏡像https://hub.docker.com/_/microsoft-dotnet - Linux 包https://github.com/dotnet/core/blob/main/release-notes/6.0/install-linux.md - 發(fā)布說明https://github.com/dotnet/core/blob/main/release-notes/6.0/README.md - API 差異https://github.com/dotnet/core/tree/main/release-notes/6.0/preview/api-diff/preview7 - 已知問題https://github.com/dotnet/core/blob/main/release-notes/6.0/known-issues.md - GitHub issue 跟蹤https://github.com/dotnet/core/issues/6554請參閱 .NET MAUI[3] 和 ASP.NET Core[4],了解更多關(guān)于客戶端和 Web 應(yīng)用場景的新內(nèi)容。
.NET 6 預(yù)覽版 7 已經(jīng)在 Visual Studio 2022 預(yù)覽版 3 中測試通過并得到支持。Visual Studio 2022 使你能夠利用為 .NET 6 開發(fā)的 Visual Studio 工具,如 .NET MAUI 的開發(fā)、C# 應(yīng)用程序的 Hot Reload、WebForms 的 Web Live,以及 IDE 體驗中的其他性能改進(jìn)。Visual Studio Code 也支持 .NET 6。
請查看我們新的對話帖[5],了解工程師之間關(guān)于最新的 .NET 功能的深入討論。我們還發(fā)表了關(guān)于 C# 10 中的字符串插值和 .NET 6 中的預(yù)覽功能 - 泛型 Math[6]。
1.NET SDK:現(xiàn)代化的 C# 項目模板
我們更新了 .NET SDK 的模板,以使用最新的 C# 語言特性和模式。我們已經(jīng)有一段時間沒有在新的語言特性方面重新審視這些模板了。現(xiàn)在是時候了,我們將確保模板在未來使用新的功能。
以下是新模板中使用的語言特性:
頂層語句
async Main
全局 using 指令(通過 SDK 驅(qū)動的默認(rèn)值)
File-scoped 命名空間
目標(biāo)類型 new 表達(dá)式
可空(Nullable)引用類型
你可能會問,為什么我們要通過模板啟用某些功能,而不是在項目以 .NET 6 為 Target 時默認(rèn)啟用這些功能。盡管我們可以要求你在升級應(yīng)用程序到新版本的 .NET 時做一些工作,作為改善平臺默認(rèn)行為的交換條件,這使我們能夠改進(jìn)產(chǎn)品,而不會使項目文件隨著時間的推移而變得復(fù)雜。然而,有些功能對于這種模式來說可能是相當(dāng)具有破壞性的,比如可空(Nullable)的引用類型。無論是在什么時候,我們都不想把這些功能與升級體驗聯(lián)系在一起,而是想把這個選擇權(quán)留給你。模板是一個風(fēng)險更低的支點,在那里我們能夠為新的代碼設(shè)置新的“好的默認(rèn)模型”,而不會產(chǎn)生那么多下游的后果。通過項目模板啟用這些功能,我們得到了兩全其美的結(jié)果:新代碼開始時啟用了這些功能,但現(xiàn)有的代碼在你升級時不會受到影響。
控制臺模板
控制臺模板變化最大,通過頂層語句和全局引用指令,它現(xiàn)在是一個單行代碼:
// See https://aka.ms/new-console-template for more information Console.WriteLine("Hello, World!");而以前的同一模板的 .NET 5 版本是這樣的:
using System;namespace?Company.ConsoleApplication1 {class?Program{static?void?Main(string[] args){Console.WriteLine("Hello, World!");}} }控制臺模板的項目文件也發(fā)生了變化,啟用了可空(Nullable)引用類型的功能,例如:
<Project?Sdk="Microsoft.NET.Sdk"><PropertyGroup><OutputType>Exe</OutputType><TargetFramework>net6.0</TargetFramework><Nullable>enable</Nullable></PropertyGroup></Project>其他模板也可以實現(xiàn)可空(Nullable)引用類型、隱式全局引用和 File-scoped 命名空間,包括 ASP.NET Core 和 類庫。
ASP.NET Web 模板
Web 模板也同樣減少了代碼行數(shù),使用同樣的功能:
var builder = WebApplication.CreateBuilder(args); var app = builder.Build();if (app.Environment.IsDevelopment()) {app.UseDeveloperExceptionPage(); }app.MapGet("/", () => "Hello World!");app.Run();ASP.NET MVC 模板
MVC 模板的結(jié)構(gòu)也類似。在這種情況下,我們將 Program.cs 和 Startup.cs 合并為一個文件(Program.cs),形成了進(jìn)一步的簡化:
var builder = WebApplication.CreateBuilder(args);// Add services to the container. builder.Services.AddControllersWithViews();var app = builder.Build();// Configure the HTTP request pipeline. if (app.Environment.IsDevelopment()) {app.UseDeveloperExceptionPage(); } else {app.UseExceptionHandler("/Home/Error");// The default HSTS value is 30 days. You may want to change this for production scenarios, see https://aka.ms/aspnetcore-hsts.app.UseHsts(); }app.UseHttpsRedirection(); app.UseStaticFiles();app.UseRouting();app.UseAuthorization();app.MapControllerRoute(name: "default",pattern: "{controller=Home}/{action=Index}/{id?}");app.Run();模板兼容性
關(guān)于使用新模板的兼容性問題,請參見以下內(nèi)容:
模板中的 C# 代碼不被早期的 .NET 版本所支持[7]
隱式命名空間引入[8]
2類庫:反射 API 的可空性信息
可空引用類型[9]是編寫可靠代碼的一個重要特征。它在編寫代碼時非常有用,但在檢查代碼時卻沒有(直到現(xiàn)在)。新的反射 API[10] 使你能夠確定一個給定方法的參數(shù)和返回值的可空性。這些新的 API 對于基于反射的工具和序列化來說是至關(guān)重要的,比如說:
就上下文而言,我們在 .NET 5 中為 .NET 庫添加了可空標(biāo)注[11](在.NET 6 中完成),并且正在為 ASP.NET Core 的這個版本做同樣的工作。我們也看到開發(fā)者在他們的項目中采用了可空性(Nullability)[12]。
可空性(Nullability)信息存在于使用自定義屬性的元數(shù)據(jù)中[13]。原則上,任何人都已經(jīng)可以讀取自定義屬性,然而,這并不理想,因為編碼的消耗非同小可。
下面的例子演示了在幾個不同的場景中使用新的 API。
獲取頂層的可空性信息
想象一下,你正在實現(xiàn)一個序列化器。使用這些新的 API,序列化器可以檢查一個給定的屬性是否可以被設(shè)置為 null:
private NullabilityInfoContext _nullabilityContext = new NullabilityInfoContext();private?void?DeserializePropertyValue(PropertyInfo p, object instance, object? value) {if (value?is?null){var nullabilityInfo = _nullabilityContext.Create(p);if (nullabilityInfo.WriteState is?not NullabilityState.Nullable){throw?new MySerializerException($"Property '{p.GetType().Name}.{p.Name}'' cannot be set to null.");}}p.SetValue(instance, value); }獲取嵌套的可空性信息
可空性對可以持有其他對象的對象有特殊處理,比如數(shù)組和元組。例如,你可以指定一個數(shù)組對象(作為一個變量,或者作為一個類型成員簽名的一部分)必須是非空的,但是元素可以是空的,或者相反。這種額外的特殊性是可以通過新的反射 API 來檢查的,例如:
class?Data {public?string?[] ArrayField;public (string?, object) TupleField; } private?void?Print() {Type type = typeof(Data);FieldInfo arrayField = type.GetField("ArrayField");FieldInfo tupleField = type.GetField("TupleField");NullabilityInfoContext context = new ();NullabilityInfo arrayInfo = context.Create(arrayField);Console.WriteLine(arrayInfo.ReadState); // NotNullConsole.WriteLine(arrayInfo.Element.State); // NullableNullabilityInfo tupleInfo = context.Create(tupleField);Console.WriteLine(tupleInfo.ReadState); // NotNullConsole.WriteLine(tupleInfo.GenericTypeArguments [0].State); // NullableConsole.WriteLine(tupleInfo.GenericTypeArguments [1].State); // NotNull }3類庫:ZipFile 遵循 Unix 文件權(quán)限
System.IO.Compression.ZipFile 類現(xiàn)在可以在創(chuàng)建過程中捕獲 Unix 文件權(quán)限,并在類似 Unix 的操作系統(tǒng)上提取壓縮文件時設(shè)置文件權(quán)限。這一變化允許可執(zhí)行文件在壓縮包中被循環(huán)使用,這意味著你不再需要修改文件權(quán)限來使文件在解壓縮包后可執(zhí)行。它也同樣遵循 user、group 和 other 讀/寫權(quán)限。
如果一個壓縮包不包含文件權(quán)限(因為它是在 Windows 上創(chuàng)建的,或者使用了一個沒有捕獲權(quán)限的工具,比如早期的 .NET 版本),那么解壓縮的文件就會得到默認(rèn)的文件權(quán)限,就像其他新創(chuàng)建的文件一樣。
Unix 的文件權(quán)限也適用于其他壓縮工具,包括:
Info-ZIP
7-Zip
4早期 .NET 7 功能預(yù)覽:泛型 Math
對于 .NET 6,我們已經(jīng)建立了將 API 標(biāo)記為“預(yù)覽”的能力[14]。這種新方法將使我們能夠在多個主要版本中提供和發(fā)展預(yù)覽功能。為了使用預(yù)覽 API,項目需要明確選擇使用的預(yù)覽功能。如果你在沒有明確選擇的情況下使用預(yù)覽功能,從 .NET 6 RC1 開始,你會看到帶有可操作信息的構(gòu)建錯誤。預(yù)覽功能預(yù)計將在以后的版本中發(fā)生變化,可能會有破壞性的變化。這就是為什么他們要選擇加入。
我們在 .NET 6 中預(yù)覽的這些功能之一是靜態(tài)抽象接口成員。這些允許你在接口中定義靜態(tài)的抽象方法(包括操作符)。例如,現(xiàn)在可以實現(xiàn)代數(shù)泛型方法。對于一些人來說,這個功能將是我們今年交付的絕對突出的改進(jìn)。這也許是自 Span<T> 以來最重要的新類型系統(tǒng)特性。
下面的例子是一個 IEnumerable<T>,由于 T 被限制為 INumber<T>,可能是一個 INumber<int>,所以能夠?qū)λ械臄?shù)值進(jìn)行求和。
public?static T Sum<T>(IEnumerable<T> values)where T : INumber<T> {T result = T.Zero;foreach (var?value?in values){result += value;}return result; }這是因為 INumber<T> 定義了各種(靜態(tài))操作符重載,必須由接口實現(xiàn)者來滿足。IAdditionOperators 也許是最容易理解的新接口,INumber<T> 本身就是派生自這個接口。
這都是由一個新的功能提供的,它允許在接口中聲明靜態(tài)抽象成員。這使得接口可以公開運算符和其他靜態(tài)方法,比如 Parse 或 Create,并且這些方法可以由派生類型實現(xiàn)。更多細(xì)節(jié)請參見我們的相關(guān)博文[15]。
所有提到的功能都是 .NET 6 的預(yù)覽版,不支持在生產(chǎn)中使用。我們將感謝您在使用中提供反饋。我們打算在 .NET 7 中繼續(xù)發(fā)展和改進(jìn)泛型 Math 功能以及支持它們的運行時和 C# 功能。我們希望對當(dāng)前的體驗進(jìn)行突破性的改變,這也是為什么新的 API 被標(biāo)記為“預(yù)覽”的部分原因。
5類庫:NativeMemory API
我們增加了新的本地內(nèi)存分配 API[16],通過 System.Runtime.InteropServices.NativeMemory 公開。這些 API 相當(dāng)于 C 語言中的 malloc、free、realloc 和 calloc API,還包括用于進(jìn)行對齊分配的 API。
你可能想知道如何看待這些 API。首先,它們是低級別的 API,是為低級別的代碼和算法準(zhǔn)備的。應(yīng)用程序開發(fā)人員很少會用到這些。另一種思考這些 API 的方式類似于平臺內(nèi)部的 API,它們是用于 CPU 指令的低級別 .NET API。這些 API 是類似的,但它是為內(nèi)存相關(guān)的操作暴露的低級別的 API。
6類庫:System.Text.Json 序列化通知
System.Text.Json 序列化器現(xiàn)在將通知作為(反)序列化操作的一部分公開。它們對于默認(rèn)值和驗證非常有用。要使用它們,請在 System.Text.Json.Serialization 命名空間中實現(xiàn)一個或多個接口 IJsonOnDeserialized、IJsonOnDeserializing、IJsonOnSerialized 或 IJsonOnSerializing`。
這里有一個例子,在 JsonSerializer.Serialize() 和 JsonSerializer.Deserialize() 中都進(jìn)行驗證,以確保 FirstName 屬性不是 null。
public?class?Person : IJsonOnDeserialized, IJsonOnSerializing {public?string FirstName{ get; set; }void IJsonOnDeserialized.OnDeserialized() => Validate(); // Call after deserializationvoid IJsonOnSerializing.OnSerializing() => Validate(); // Call before serializationprivate?void?Validate(){if (FirstName is?null){throw?new InvalidOperationException("The 'FirstName' property cannot be 'null'.");}} }以前,你需要實現(xiàn)一個自定義轉(zhuǎn)換器來實現(xiàn)這一功能。
7類庫:System.Text.Json 序列化屬性排序
我們使用 System.Text.Json.Serialization.JsonPropertyOrderAttribute 特性增加了控制屬性序列化順序的能力,用一個整數(shù)指定了順序,較小的整數(shù)先被序列化;沒有該特性的屬性有一個默認(rèn)的排序值 0。
這里有一個例子,指定 JSON 應(yīng)該按照 Id, City, FirstName, LastName 的順序進(jìn)行序列化:
public?class?Person {public?string City { get; set; } // No order defined (has the default ordering value of 0)[JsonPropertyOrder(1)] // Serialize after other properties that have default orderingpublic?string FirstName { get; set; }[JsonPropertyOrder(2)] // Serialize after FirstNamepublic?string LastName { get; set; }[JsonPropertyOrder(-1)] // Serialize before other properties that have default orderingpublic?int Id { get; set; } }以前,序列化順序是由反射順序決定的,而反射順序既不是確定的,也不會導(dǎo)致特定的預(yù)期順序。
8類庫:System.Text.Json.Utf8JsonWriter
在用 Utf8JsonWriter 編寫 JSON payloads 時,有時你需要嵌入“原始”JSON。
比如:
我有一個設(shè)計好的字節(jié)序列,如下例所示。
我有一個 blob,我認(rèn)為它代表 JSON 內(nèi)容,我想把它包起來,我需要確保包和它的內(nèi)部保持良好的格式。
以下是對上述代碼--特別是FormatNumberValue--的描述。為了提高性能,System.Text.Json 在數(shù)字為整數(shù)時省略了小數(shù)點/值,如 1.0。其理由是,寫的字節(jié)數(shù)越少越好,有利于提高性能。在某些情況下,保留小數(shù)點可能很重要,因為消費者將沒有小數(shù)點的數(shù)字視為整數(shù),否則視為浮點數(shù)。這種新的“原始值”模型允許你在任何需要的地方擁有這種程度的控制。
9類庫:JsonSerializer 同步流重載
我們?yōu)?JsonSerializer 添加了新的同步 API[17],用于將 JSON 數(shù)據(jù)序列化和反序列化到一個流。你可以在下面的例子中看到這個演示。
using MemoryStream ms = GetMyStream(); MyPoco poco = JsonSerializer.Deserialize<MyPoco>(ms);這些新的同步 API 包括與新的 System.Text.Json source generator[18] 兼容和可用的重載,通過接受 JsonTypeInfo<T> 或 JsonSerializerContext 實例。
10類庫:System.Diagnostics Propagators
在過去的幾年里,我們一直在改進(jìn)對 OpenTelemetry[19] 的支持。實現(xiàn)該支持的一個關(guān)鍵點是確保所有需要參與遙測生產(chǎn)的組件以正確的格式輸出到網(wǎng)絡(luò)頭。要做到這一點真的很難,特別是隨著 OpenTelemetry 規(guī)范的變化。OpenTelemetry 定義了傳播(propagation)[20]的概念來幫助解決這種情況。我們正在采用傳播的方式來實現(xiàn)頭的定制的一般模型。
關(guān)于更廣泛的概念背景:
OpenTelemetry 規(guī)范 - 分布式跟蹤數(shù)據(jù)結(jié)構(gòu)的內(nèi)存表示。
OpenTelemetry Span - 追蹤構(gòu)建塊,在 .NET 中由 System.Diagnostics.Activity 表示。
W3C TraceContext - 關(guān)于如何通過眾所周知的 HTTP 頭傳播這些分布式跟蹤數(shù)據(jù)結(jié)構(gòu)的規(guī)范。
下面的代碼演示了使用傳播的一般方法:
DistributedContextPropagator propagator = DistributedContextPropagator.Current; propagator.Inject(activity, carrier, (object theCarrier, string fieldName, string?value) => {// Extract the context from the activity then inject it to the carrier. });你也可以選擇使用不同的傳播器(propagator):
// Set the current propagation behavior to not transmit any distributed context information in outbound network messages. DistributedContextPropagator.Current = DistributedContextPropagator.CreateNoOutputPropagator();DistributedContextPropagator 抽象類決定了分布式上下文信息在網(wǎng)絡(luò)傳輸時是否以及如何被編碼和解碼。編碼可以通過任何支持字符串鍵/值對的網(wǎng)絡(luò)協(xié)議進(jìn)行傳輸。DistributedContextPropagator 以字符串鍵/值對的形式向載體注入數(shù)值并從載體中提取數(shù)值。通過添加對傳播者的支持,我們實現(xiàn)了兩件事。
你不再需要使用 W3C 的 TraceContext 頭文件。你可以編寫一個自定義的傳播器(甚至用你自己的頭文件名稱),而不需要 HttpClient、ASP.NET Core 等庫對這種自定義格式有預(yù)先的了解。
如果你實現(xiàn)了一個帶有自定義傳輸?shù)膸?#xff08;如消息隊列),只要你支持發(fā)送和接收文本映射(如 Dictionary<string, string>),你現(xiàn)在可以支持各種格式。
大多數(shù)應(yīng)用程序代碼不需要直接使用這個功能,然而,如果你使用 OpenTelemetry,你很可能會在調(diào)用棧中看到它。一些庫的代碼如果關(guān)心跟蹤和因果關(guān)系,可能會需要使用這個模型。
11類庫:加密操作調(diào)用模式簡化
.NET 的加密和解密部件是圍繞著流設(shè)計的,沒有真正的概念來定義什么時候有效載荷已經(jīng)在內(nèi)存中(already in memory)。SymmetricAlgorithm 上新的 Encrypt- 和 Decrypt- 方法加速了 already in memory 的進(jìn)展,目的是為調(diào)用者和代碼審查者提供清晰的信息。此外,它們還支持從 span 中讀取和寫入。
新的簡化方法為使用加密 API 提供了一個直接的方法:
private?static?byte[] Decrypt(byte[] key, byte[] iv, byte[] ciphertext) {using (Aes aes = Aes.Create()){aes.Key = key;return aes.DecryptCbc(ciphertext, iv);} }在新的 Encrypt- 和 Decrypt- 方法中,只使用 SymmetricAlgorithm 實例中的 Key 屬性。新的 DecryptCbc 方法支持選擇填充算法,但是 PKCS#7 經(jīng)常與 CBC 一起使用,所以它是一個默認(rèn)參數(shù)。如果你喜歡這種清晰的感覺,就指定它吧:
private?static?byte[] Decrypt(byte[] key, byte[] iv, byte[] ciphertext) {using (Aes aes = Aes.Create()){aes.Key = key;return aes.DecryptCbc(ciphertext, iv, PaddingMode.PKCS7);} }你可以看到,現(xiàn)有的模式--使用 .NET 5--明顯需要更多的管道來實現(xiàn)同樣的結(jié)果:
private?static?byte[] Decrypt(byte[] key, byte[] iv, byte[] ciphertext) {using (Aes aes = Aes.Create()){aes.Key = key;aes.IV = iv;// These are the defaults, but let's set them anyways.aes.Padding = PaddingMode.PKCS7;aes.Mode = CipherMode.CBC;using (MemoryStream destination = new MemoryStream())using (ICryptoTransform transform = aes.CreateDecryptor())using (CryptoStream cryptoStream = new CryptoStream(destination, transform, CryptoStreamMode.Write)){cryptoStream.Write(ciphertext, 0, ciphertext.Length);cryptoStream.FlushFinalBlock();return destination.ToArray();}} }12運行時:支持所有平臺和架構(gòu)的 W^X
運行時現(xiàn)在有一種模式,它不創(chuàng)建或使用任何同時可寫和可執(zhí)行的內(nèi)存頁。所有可執(zhí)行的內(nèi)存都被映射為只讀不執(zhí)行。這項功能在該版本的早期僅在 macOS 上啟用--針對 Apple Silicon。在 Apple Silicon 機器上,禁止同時進(jìn)行可寫和可執(zhí)行的內(nèi)存映射。
這一功能現(xiàn)在在所有其他平臺上被啟用并支持。在這些平臺上,可執(zhí)行代碼的生成/修改是通過單獨的讀寫內(nèi)存映射完成的,這對 JIT 代碼和運行時生成的輔助程序都是如此。這些映射是在與可執(zhí)行代碼地址不同的虛擬內(nèi)存地址上創(chuàng)建的,并且只在進(jìn)行寫入時存在非常短暫的時間。例如,JIT 現(xiàn)在生成代碼到一個從頭開始的緩沖區(qū),在整個方法被 jitted 后,使用一個內(nèi)存拷貝函數(shù)調(diào)用將其復(fù)制到可執(zhí)行內(nèi)存中。而可寫映射的壽命只跨越了內(nèi)存拷貝的時間。
這個新功能可以通過設(shè)置環(huán)境變量 DOTNET_EnableWriteXorExecute 為 1 來啟用。這個功能在 .NET 6 中是可選的,因為它有一個啟動時的退步(除了在 Apple Silicon 上)。在我們的 ASP.NET 基準(zhǔn)測試中,當(dāng)用 Ready To Run(R2R)編譯時,退步了 ~10%。然而,在啟用和未啟用該功能的情況下,測得的穩(wěn)態(tài)性能是一樣的。對于啟動性能并不重要的應(yīng)用程序,我們建議啟用該功能,因為它能提高安全性。我們打算作為 .NET 7 的一部分解決性能退步問題,屆時默認(rèn)啟用該功能。
13結(jié)束
我們認(rèn)為,我們已經(jīng)到了新功能和改進(jìn)已經(jīng)完成的發(fā)布點。為團(tuán)隊點贊!
我們繼續(xù)期待你們的反饋。我們將把 .NET 6 的其余部分放在完善(功能和性能)和新功能中發(fā)現(xiàn)的錯誤上。在大多數(shù)情況下,功能改進(jìn)需要等到 .NET 7。請分享你的任何反饋,我們將很高興對其進(jìn)行分類。
感謝所有為 .NET 6 做出貢獻(xiàn)的人,使其成為另一個偉大的版本。
感謝你成為一名 .NET 開發(fā)者。
文中相關(guān)鏈接:
[1].https://dotnet.microsoft.com/ [2].https://dotnet.microsoft.com/download/dotnet/6.0 [3].https://devblogs.microsoft.com/dotnet/announcing-net-maui-preview-7/ [4].https://devblogs.microsoft.com/aspnet/asp-net-core-updates-in-net-6-preview-7/ [5].https://devblogs.microsoft.com/dotnet/category/conversations/ [6].https://devblogs.microsoft.com/dotnet/string-interpolation-in-c-10-and-net-6/ [7].https://docs.microsoft.com/dotnet/core/compatibility/sdk/6.0/csharp-template-code [8].https://docs.microsoft.com/dotnet/core/compatibility/sdk/6.0/implicit-namespaces [9].https://docs.microsoft.com/dotnet/csharp/nullable-references [10].https://github.com/dotnet/runtime/issues/29723 [11].https://twitter.com/JeffHandley/status/1424846146850131968 [12].https://github.com/jellyfin/jellyfin/blob/c07e83fdf87e61f30e4cca4e458113ac315918ae/Directory.Build.props#L5 [13].https://github.com/dotnet/roslyn/blob/main/docs/features/nullable-metadata.md [14].https://github.com/dotnet/designs/blob/main/accepted/2021/preview-features/preview-features.md [15].https://devblogs.microsoft.com/dotnet/preview-features-in-net-6-generic-math/ [16].https://github.com/dotnet/runtime/pull/54006 [17].https://github.com/dotnet/runtime/issues/1574 [18].https://devblogs.microsoft.com/dotnet/try-the-new-system-text-json-source-generator/ [19].https://devblogs.microsoft.com/dotnet/opentelemetry-net-reaches-v1-0/ [20].https://opentelemetry.lightstep.com/core-concepts/context-propagation/總結(jié)
以上是生活随笔為你收集整理的.NET 6 预览版 7 发布--(最后一个预览版)的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 在 ASP.NET Core 中使用 S
- 下一篇: 设计模式之代理