LINQ ANY()与First()和FirstOrDefault()

时间:2018-02-20 07:52:58

标签: c# .net performance linq

我已经编写了这样的代码

TotalCashIn = totals != null && totals.Any() ? totals.First().TotalCashIn : null;

我被指责这个代码,并告诉写这样的

TotalCashIn = totals != null ? totals.FirstOrDefault().TotalCashIn : null;

但我想知道如果总计计数为0,我不会得到例外吗?  我是否还需要使用.Any().Count()

进行检查

3 个答案:

答案 0 :(得分:13)

假设totals的元素类型是引用类型,您可以使用null-conditional operator使所有这些变得更加简单:

TotalCashIn = totals?.FirstOrDefault()?.TotalCashIn;

有了这个:

  • 如果totals为null,则由于第一个null-conditonal运算符,整体结果为null
  • 如果totals为空,FirstOrDefault()将返回null,因此由于第二个空条件运算符,整体结果为null
  • 否则,结果是第一个元素的TotalCashIn属性

答案 1 :(得分:0)

取决于totalsIEnumerable还是IQueryable。如果是IQueryable,那么您还可以使用以下内容:

TotalCashIn = totals?.Select(t => (int?)t.TotalCashIn).FirstOrDefault();

如果您只选择所需的字段而不是表中的所有列,那会更好。

答案 2 :(得分:0)

如果totals是引用类型对象,那么FirstOrDefault可能会返回null,因此您无法调用TotalCashIn。

另一方面,如果总计是值类型,则FirstOrDefault将返回实际值,您可以调用TotalCashIn。例如,如果总计是一个整数序列,那么FirstOrDefault将返回零(不为空!)。

如果TotalCashIn是int的扩展函数,那么如果在FirstOrDefault之后调用TotalCashIn是完美的:

IEnumerable<int> totals = ...
int firstInt = totals.FirstOrDefault();
var totalCashIn = firstInt.TotalCashIn(); // extension function of int

或在一个声明中:

var totalCashIn = totals.FirstOrDefault().TotalCashIn();

使用空条件运算符(?。)是否明智取决于TotalCashIn的定​​义,特别是如果您的集合根本没有元素。

如果您说:&#34; TotalCashIn表示我兑现的金额...&#34;,则TotalCashIn可能具有零值,但不是空值。

如果在空集合的情况下想要零值,请考虑使用Select在FirstOrDefault之前选择所需的属性:

var totalCashIn = totals.Select(item => item.TotalCashIn).FirstOrDefault();

如果属性TotalCashIn是值类型,那么如果您的总计集合为空,则它将返回零

在您询问是否使用Count()或Any()时:永远不要使用Count()来测试您的序列是否包含任何元素,除非您确定您的输入序列是ICollection。如果在您已经知道有元素的第一个元素之后,访问序列的所有元素实际上是浪费计算能力。