如何避免“对不可为空的实体进行可能的“空”分配”

发布于 2025-01-09 04:34:24 字数 695 浏览 1 评论 0原文

抱歉这个尴尬的例子,但我想尽可能保持它的重点

可以说,我已经解析了一个 json 文件,它给了我

var customers = myObj.SubObj?.CustomerList.EmptyIfNull();
var plusCustomers = customers.Where(...) // Resharper warning

myobj 下面的层次结构不能为空 有时 SubObject 可以为 null

我有一个扩展方法

IEnumerable<T> EmptyIfNull<T>(this IEnumerable<T> enumerable) => enumerable ?? Enumerable.Empty<T>();

所以我希望 plusCustomers 行是安全的(空列表而不是 null)。但我收到警告

可能对不可为 null 的实体进行“null”赋值

如果我将第一行替换为,

var customers = myObj.SubObj.CustomerList.EmptyIfNull();

我就会消除警告,但这是不正确的。我怎样才能让 Resharper 相信这没问题?...或者我错了?

Sorry for this awkward example, but I want to keep it as to the point as possible

Lets say, I have parsed a json-file, which gives me the hierarchy below

var customers = myObj.SubObj?.CustomerList.EmptyIfNull();
var plusCustomers = customers.Where(...) // Resharper warning

myobj cannot be null
SubObject can be null sometimes

I have an extension method

IEnumerable<T> EmptyIfNull<T>(this IEnumerable<T> enumerable) => enumerable ?? Enumerable.Empty<T>();

So I expect the plusCustomers-line to be safe(empty list instead of null). But I get a warning

possible "null"assignment to a non-nullable entity

If I replace the first line with

var customers = myObj.SubObj.CustomerList.EmptyIfNull();

I get rid of the warning, but that is not correct. How can I convince Resharper that this is ok?...or I'm I mistaken?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

小帐篷 2025-01-16 04:34:24

您可以添加括号:

(myObj.SubObj?.CustomerList).EmptyIfNull();

如果 LHS 操作数为 null,则空链接 (?.) 的作用是将成员访问的整个链评估为 null,而不是仅将该单个成员访问评估为 null。例如,考虑一长串成员访问abcdef。如果只有 a 可为空,则只需在 a 之后编写 ? 即可确保安全。如果 a 为 null,它不仅仅将 a?.b 计算为 null,因为在这种情况下,您必须在之后编写 ?为了安全起见,每个成员都可以访问,这有点烦人。

因此,如果没有括号,由于 ?. ,整个成员访问都可以为空,无论您最后调用什么。

通过添加括号,您可以打破成员访问链,以便 myObj.SubObj?.CustomerList 属于可为 null 的类型,并按预期调用 EmptyIfNull -返回 EmptyIfNull 应该返回的任何类型。

You can add brackets:

(myObj.SubObj?.CustomerList).EmptyIfNull();

The effect of the null chaining (?.) is to evaluate the whole chain of member accesses to null, if the LHS operand is null, rather than evaluating just that single member access to null. For example, consider a long chain of member accesses a.b.c.d.e.f. If only a is nullable, you would only need to write ? after a for this to be safe. It doesn't just evaluate a?.b to null if a is null, because in that case you'd have to write ? after every member access for this to be safe, and that's a bit annoying.

So without the brackets, the whole member access is made nullable due to ?., regardless of what you call at the end.

By adding brackets, you break up the chain of member accesses, so that myObj.SubObj?.CustomerList is of a nullable type, and calling EmptyIfNull on that works as expected - returning whatever type EmptyIfNull should return.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文