Это довольно длинный ответ, и информация в этом документе может быть изменена, так как C # 8 и инструменты Visual Studio все еще находятся в предварительном просмотре. Я постараюсь держать ответ в курсе, если что-то изменится.
Короче говоря, на момент написания статьи C # 8 можно использовать с .NET Framework в Visual Studio 2019 Preview, и я ожидаю, что так будет и впредь, но я бы не поставил на это ферму. Не все функции будут доступны - в частности .NET Framework никогда не будет поддерживать методы интерфейса по умолчанию.
Пожалуйста, перейдите к концу этого ответа, если вы просто хотите увидеть код.
Язык C # исторически в основном не зависел от фреймворка - т.е. мог компилировать более старые версии Framework - хотя некоторые функции требовали поддержки новых типов или CLR. На этот раз .NET Framework не получит никаких новых типов, если они не отображаются в виде пакетов Nuget.
Я полагаю, что большинство энтузиастов C # уже прочитали запись в блоге Building C # 8.0 от Mads Torgersen, которая объясняет, что некоторые функции C # 8 имеют зависимости от платформы:
Асинхронные потоки, индексаторы и диапазоны зависят от новых типов инфраструктуры.
это будет частью .NET Standard 2.1 ... .NET Core 3.0, а также
Xamarin, Unity и Mono будут реализовывать .NET Standard 2.1, но .NET
Framework 4.8 не будет. Это означает, что типы, необходимые для использования
эти функции не будут доступны в .NET Framework 4.8.
Итак, пока это выглядит как кортежи значений , которые были представлены в C # 7. Для этой функции требовались новые типы - ValueTuple
структуры - которые не были доступны в версиях NET Framework ниже 4.7 или .NET Standard старше 2.0. Однако , C # 7 все еще можно использовать в более старых версиях .NET, без кортежей значений или вместе с ними, установив пакет System.ValueTuple Nuget . Visual Studio это поняла, и с миром все было в порядке.
Я ожидал, что C # 8 будет работать таким же образом - нацеливаться на любую среду, в которой вы нуждаетесь, но некоторые функции не будут доступны, и Visual Studio поможет вам убедиться, что вы не пишете код, который может ' т компилировать. Однако, с тревогой, Мэдс также писал:
По этой причине использование C # 8.0 поддерживается только на платформах, которые реализуют .NET Standard 2.1.
... что исключало бы использование C # 8 с любой версией .NET Framework и даже в библиотеках .NET Standard 2.0, которые только недавно нам предложили использовать в качестве базовой цели для код библиотеки. Вы даже не сможете использовать его с версиями .NET Core старше 3.0, поскольку они также поддерживают только .NET Standard 2.0.
Я много копался, поскольку это утверждение не соответствовало моему собственному опыту использования C # 8 и обнуляемых ссылочных типов в многочисленных проектах .NET Standard 2.0 (и помните, .NET Standard это просто список API; если проект .NET 4.8 использует библиотеку .NET Standard 2.0, код будет выполняться в .NET CLR / с использованием API .NET Framework).
Вот некоторые вещи, которые я нашел:
У Джона Скита есть альфа-версия Noda-Time, использующая C # 8 готовая к работе , предназначенная только для .NET Standard 2.0. Он явно ожидает, что C # 8 / .NET Standard 2.0 будет поддерживать все платформы семейства .NET. (См. Также сообщение Джона в блоге "Первые шаги с типами ссылок, которые могут быть недействительными" ).
Сотрудники Microsoft обсуждали пользовательский интерфейс Visual Studio для обнуляемых ссылочных типов C # 8 на GitHub , и заявлено, что они намерены поддерживать устаревшую csproj
(до .NET Core Формат SDK csproj
). Это очень убедительный признак того, что C # 8 будет использоваться с .NET Framework.
Вскоре после известной публикации в блоге GitHub-ветка обсуждала межплатформенную поддержку. Важным моментом, который возник, было то, что .NET Standard 2.1 будет включать маркер, обозначающий, что поддерживаются реализации интерфейсов по умолчанию - функция требует изменения CLR, которое никогда не будет доступно .NET Framework. Вот важный момент, от Иммо Ландверта, менеджера программ в команде .NET в Microsoft:
Компиляторы (такие как C #), как ожидается, будут использовать наличие этого поля, чтобы решить, разрешать ли реализации интерфейса по умолчанию. Если поле присутствует, ожидается, что среда выполнения сможет загружать и выполнять полученный код.
Все это указывает на то, что «C # 8.0 поддерживается только на платформах, которые реализуют .NET Standard 2.1», что является чрезмерным упрощением, и что C # 8 будет поддерживать .NET Framework , но, как есть так много неопределенности, я спросил на GitHub . Пока у меня есть один ответ от HaloFour:
IIRC, единственная функция, которая определенно не появится в .NET Framework, - это DIM (методы интерфейса по умолчанию), поскольку она требует изменений во время выполнения. Другие функции определяются формой классов, которые никогда не могут быть добавлены в .NET Framework, но могут быть заполнены с помощью собственного кода или NuGet (диапазоны, индексы, асинхронные итераторы, асинхронное удаление).
Эссе закончено, давайте посмотрим на некоторый код. Следующий проект C #, нацеленный на .NET 4.8 и использующий ссылочные типы C # 8, компилируется в Visual Studio 16.2.0 Preview 3. Я создал его, выбрав шаблон .NET Standard Class Library и затем вместо этого отредактировав его для целевого .NET:
.csproj:
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFrameworks>net48</TargetFrameworks>
<LangVersion>8.0</LangVersion>
<Nullable>enable</Nullable>
</PropertyGroup>
</Project>
.cs:
namespace ClassLibrary1
{
public class Class1
{
public string? NullableString { get; set; }
}
}
Затем я попробовал WinNET-проект .NET 4.5.2, используя устаревший формат .csproj
, и добавил то же свойство ссылочного типа, допускающее обнуляемость. Я изменил тип языка в диалоговом окне настроек Visual Studio Advanced Build на latest
и сохранил проект. Конечно, как этот пункт он не строит. Я открыл файл проекта в текстовом редакторе и изменил latest
на preview
в конфигурации сборки PropertyGroup
:
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
<LangVersion>preview</LangVersion>
Затем я включил поддержку необнуляемых ссылочных типов, добавив <Nullable>enable</Nullable>
к основному PropertyGroup
:
<PropertyGroup>
<Nullable>enable</Nullable>
Я перезагрузил проект, и он собирается.
Поэтому я могу подтвердить, что по крайней мере на момент написания C # 8 поддерживает .NET Framework, но инструментальные средства Visual Studio не догнали. Microsoft работает над инструментальными средствами, в том числе для устаревших csproj
формат файлов.