1. Введение
Почему NRT нужно включать отдельно?
Nullable Reference Types (NRT) — это не просто синтаксический сахар, а серьёзный помощник компилятора в борьбе с ошибками, связанными с null. Но по историческим причинам этот режим не включён по умолчанию во всех старых проектах — чтобы не сломать совместимость. Если вы создаёте новый проект в последних версиях .NET (например, .NET 7, 8 или 9), то NRT, скорее всего, уже включены автоматически. Но если проект старенький или вы хотите управлять этим режимом вручную, это нужно сделать явно.
Что делает режим Nullable Reference Types?
Когда этот режим активен, компилятор начинает анализировать, какие ссылочные переменные могут быть равны null, а какие — нет. Он не вмешивается в выполнение программы, но щедро сыплет предупреждениями, если видит возможную ошибку. Это отличный способ написать надёжный, понятный и устойчивый код.
Как узнать, включён ли режим NRT?
Если у вас новый проект .NET 6 или выше, скорее всего, NRT уже включены. Но бывает всякое. Давайте проверим!
- Откройте файл проекта. Обычно это файл с расширением .csproj.
- Найдите или добавьте настройку <Nullable> внутри первого тега <PropertyGroup>.
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>net9.0</TargetFramework>
<Nullable>enable</Nullable>
</PropertyGroup>
</Project>
Если там написано <Nullable>disable</Nullable>, значит контроль NRT выключен.
2. Как включить режим NRT
Через .csproj — для всего проекта
- Откройте (или создайте) файл .csproj.
- Внутри блока <PropertyGroup> добавьте или измените строку:
<Nullable>enable</Nullable>
Теперь компилятор будет внимательно следить за всеми .cs-файлами в проекте и ругаться на потенциально опасные обращения к null.
Зачем так делать?
Потому что это глобальная настройка. С этого момента весь проект работает по новым правилам: null — под подозрением, и халатность больше не пройдёт!
Только для отдельных файлов или кусков кода
Если вы пока не готовы включить строгий режим для всего проекта, можно потренироваться на отдельных файлах. Для этого используются директивы препроцессора:
#nullable enable
string? value = null; // Здесь анализ включён
#nullable disable
string legacyValue = null; // А здесь — уже нет
#nullable restore
- #nullable enable — включает проверку до конца файла.
- #nullable disable — отключает её.
- #nullable restore — возвращает настройки из .csproj или внешнего файла.
Это удобно: можно включить строгий контроль в новых модулях, не трогая старый, нестабильный код.
Что ещё можно указать в <Nullable>
| Значение | Поведение |
|---|---|
|
Включает всё: аннотации и предупреждения |
|
Полностью отключает анализ null-ссылок |
|
Только предупреждения, без обязательных аннотаций |
|
Аннотации нужны, но компилятор не будет ругаться |
|
Вернёт поведение к исходному (например, из глобальной настройки) |
Обычно используют enable или disable.
3. Демонстрация на примере
До включения NRT
// Старый режим, NRT выключен
string s = null; // Никаких жалоб
Console.WriteLine(s.Length); // Опасно! Возможен NullReferenceException
После включения NRT
// Новый режим, NRT включены
string s = null; // Warning: возможно присваивание null
Console.WriteLine(s.Length); // Warning: возможное обращение к null
Теперь IDE начнёт подчёркивать потенциальные проблемы и компилятор предупредит: Dereference of a possibly null reference. (CS8602)
Как это исправить?
string? s = null;
if (s != null)
{
Console.WriteLine(s.Length);
}
Так вы явно указываете: эта переменная может быть null, и компилятор доволен.
4. Что делать, если проект написан "по-старинке"?
Многие проекты писались в эпоху, когда null был чуть ли не в каждой ссылочной переменной. Включив NRT, вы как будто нанимаете строгого ревизора, который будет сообщать о каждой потенциальной проблеме.
А если предупреждений слишком много?
Не паникуйте — это не ошибки, а просто подсказки. Программа по-прежнему компилируется.
- Можно включать NRT только в новых файлах.
- Постепенно приводите код в порядок: добавляйте ?, делайте проверки на null, используйте ! (про это позже).
- Помните: чем аккуратнее вы работаете с null, тем меньше проблем потом.
Обратная совместимость и сторонние библиотеки
- Включение NRT не меняет поведение кода во время выполнения, только добавляет анализ на этапе компиляции.
- Старый код может сразу выдать много предупреждений.
- Если вы используете библиотеки без NRT-аннотаций, компилятор будет вести себя осторожно и предполагать, что всё может быть null.
ПЕРЕЙДИТЕ В ПОЛНУЮ ВЕРСИЮ