最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

c# - Why is there no CS8604 (Possible null reference argument for parameter) warning in .NET Standard 2.1 - Stack Overflow

programmeradmin2浏览0评论

When working with .NET Standard 2.1 code, I found a strange behaviour when there should have been a warning to a nullable parameter but it does not:

And I can reproduce it with a simple method:

#nullable enable // making sure that nullability is enabled
static void Foo(IEnumerable<string>? a = default)
{
    Console.WriteLine(a.Count());

    string? b = null;
    Console.WriteLine(b.Length);
}

With the above code compiled in netstandard2.1, there is no warning for a. Nullable context does work because there is CS8602 (dereference of a possibly null reference) for b.

When switching to net8.0 for example, the compiler correctly raises CS8604 for a. This is built using .NET 9 SDK.

What's going on here? Is it a bug in the compiler?

When working with .NET Standard 2.1 code, I found a strange behaviour when there should have been a warning to a nullable parameter but it does not:

And I can reproduce it with a simple method:

#nullable enable // making sure that nullability is enabled
static void Foo(IEnumerable<string>? a = default)
{
    Console.WriteLine(a.Count());

    string? b = null;
    Console.WriteLine(b.Length);
}

With the above code compiled in netstandard2.1, there is no warning for a. Nullable context does work because there is CS8602 (dereference of a possibly null reference) for b.

When switching to net8.0 for example, the compiler correctly raises CS8604 for a. This is built using .NET 9 SDK.

What's going on here? Is it a bug in the compiler?

Share Improve this question edited Feb 16 at 15:58 Luke Vo asked Feb 16 at 15:38 Luke VoLuke Vo 20.7k25 gold badges125 silver badges230 bronze badges 4
  • 2 Does .NET Standard 2.1 have nullability annotations at all? For example, do you get a warning for calling string.IsInterned(null)? If not, that's probably the problem. Bear in mind that the LINQ methods are extension methods, so they could be declared to accept a null first argument... unless the compiler see that the assembly is annotated with NRT annotations, it can't/shouldn't warn. – Jon Skeet Commented Feb 16 at 15:53
  • @JonSkeet Please disregard my previous comment. actually you are right, with a being string?, using a.Length would cause the warning, while a.Count() would not. So yes it's due to extension method. And in my screenshot, Append indeed is an extension method as well. – Luke Vo Commented Feb 16 at 15:59
  • Right, so it sounds like it's "just" a matter of .NET Standard 2.1 not being annotated. Oddly, in the documentation, there's a difference between ".NET Standard 2.1" and ".NET Standard 2.1 (package-provided)" but I can't see any details of what that "package-provided" means. – Jon Skeet Commented Feb 16 at 16:00
  • @JonSkeet Yes I knew .NET Standard 2.1 is not annotated but I didn't catch that it's due to extension method. I thought it's strange that an instance that is clearly null there is not getting any warning. Great find there. – Luke Vo Commented Feb 16 at 16:03
Add a comment  | 

1 Answer 1

Reset to default 2

.NET standard does not have nullability annotations. It does not use the nullable reference types feature. It's as if you are using a library that has #nullable disable.

For example, compare how the EqualityComparer<T>.Equals method is declared. In .NET 9, it's

public abstract bool Equals (T? x, T? y);

In .NET Standard, it's

public abstract bool Equals (T x, T y);

The same goes for the the parameter of the Enumerable.Count method - it's just that "not nullable" (in a #nullable enable environment) is syntactically the same as "not annotated" (in a #nullable disable environment), so there is no visual difference.

Therefore, the compiler is oblivious to what can and can't be null in all the .NET Standard APIs, and the compiler is designed to not raise warnings in such a situation. Otherwise (if the compiler assumes everything is nullable) you will likely get a lot of warnings when you try to use an old, unannotated library.

See also this GitHub issue, which says that it is not planned for .NET Standard to get nullable annotations in the future.

与本文相关的文章

发布评论

评论列表(0)

  1. 暂无评论