为什么该代码给出“可能的空引用返回"?编译器警告? [英] Why does this code give a "Possible null reference return" compiler warning?
问题描述
考虑以下代码:
using System;
#nullable enable
namespace Demo
{
public sealed class TestClass
{
public string Test()
{
bool isNull = _test == null;
if (isNull)
return "";
else
return _test; // !!!
}
readonly string _test = "";
}
}
构建此文件时,标有!!!
的行会发出编译器警告:warning CS8603: Possible null reference return.
.
When I build this, the line marked with !!!
gives a compiler warning: warning CS8603: Possible null reference return.
.
鉴于_test
是只读的并且已初始化为非null,因此我对此感到有些困惑.
I find this a little confusing, given that _test
is readonly and initialised to non-null.
如果我将代码更改为以下内容,则警告消失:
If I change the code to the following, the warning goes away:
public string Test()
{
// bool isNull = _test == null;
if (_test == null)
return "";
else
return _test;
}
任何人都可以解释这种行为吗?
Can anyone explain this behaviour?
推荐答案
可为空的流分析会跟踪变量的空状态,但不会跟踪其他状态,例如bool
变量(如上面的isNull
一样),它不会跟踪单独变量(例如isNull
和_test
)的状态之间的关系.
The nullable flow analysis tracks the null state of variables, but it does not track other state, such as the value of a bool
variable (as isNull
above), and it does not track the relationship between the state of separate variables (e.g. isNull
and _test
).
一个实际的静态分析引擎可能会做这些事情,但是在某种程度上也可能是启发式"或任意性"的:您不一定要告诉它遵循的规则,而且这些规则甚至可能随着时间而改变.
An actual static analysis engine would probably do those things, but would also be "heuristic" or "arbitrary" to some degree: you couldn't necessarily tell the rules it was following, and those rules might even change over time.
这不是我们可以直接在C#编译器中执行的操作.可空警告的规则非常复杂(正如乔恩的分析所示!),但是它们是规则,并且可以进行推理.
That's not something we can do directly in the C# compiler. The rules for nullable warnings are quite sophisticated (as Jon's analysis shows!), but they are rules, and can be reasoned about.
当我们推出该功能时,感觉好像我们大多数时候已经达到了适当的平衡,但是确实有些尴尬的地方出现了,我们将在C#9.0中进行重新讨论.
As we roll out the feature it feels like we mostly struck the right balance, but there are a few places that do come up as awkward, and we'll be revisiting those for C# 9.0.
这篇关于为什么该代码给出“可能的空引用返回"?编译器警告?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!