序列为空时序列不包含任何元素

时间:2020-02-24 08:24:38

标签: c# entity-framework linq .net-core

此处的ExtraTime表示篮球中的额外时间。由于大多数比赛都没有多余的时间,因此ExtraTime将多次为空。

我搜索了其他问题并写了这个,它奏效了。该代码检查是否还有多余的时间,如果没有,则将其设置为0。并且在计算平均值时不包括0。

OverTime = Math.Round(dtos.Select(p => (decimal)(p.ExtraTimeHomeTeamScore ?? 0)).Where(p => p != 0).Average(), 2),

然后我尝试做一些更复杂的事情。这个用来检查两种不同的数据类型并计算它们的平均值。也不要包含0。由于某种原因,它返回序列错误。

 OverTime = Math.Round((decimal)(dtos.Where(p => p.DataType == 0).Select(p => p.ExtraTimeHomeTeamScore ?? 0).Where( p => p != 0).Average()
                        + dtos.Where(p => p.DataType == 1).Select(p => p.ExtraTimeAwayTeamScore ?? 0).Where(p => p != 0).Average()) / 2, 2)

我试图像第一个代码一样编写。无论我做什么,我都无法摆脱序列不包含任何元素错误。我的代码的哪一部分是错误的,可以改进?

2 个答案:

答案 0 :(得分:2)

很显然,您不能Average一无所有

但是您可以使用Enumerable.DefaultIfEmpty

返回IEnumerable<T>的元素或默认值 单例集合,如果序列为空。

var result = dtos.Where(p => p.DataType == 0)
                 .Select(p => p.ExtraTimeHomeTeamScore ?? 0)
                 .Where( p => p != 0)
                 .DefaultIfEmpty(0)
                 .Average();

答案 1 :(得分:1)

查看IEnumerable.Average文档:

例外

ArgumentNullException

source为空。

InvalidOperationException

源不包含任何元素。

您的问题是您的过滤器(where子句)什么也不返回。因此,当结果枚举不包含元素时,它们的平均值是多少?

我会做这样的事情:

var filteredDtos1 = dtos.Where(p => p.DataType == 0).Select(p => p.ExtraTimeHomeTeamScore ?? 0).Where( p => p != 0);
var filteredDtos2 = dtos.Where(p => p.DataType == 1).Select(p => p.ExtraTimeAwayTeamScore ?? 0).Where(p => p != 0).Average();

var avg1 = filteredDtos1.Count > 0 : filteredDtos1.Average ? //some default value probably 0;
var avg2 = filteredDtos2.Count > 0 : filteredDtos2.Average ? //some default value probably 0;

OverTime = Math.Round((decimal)(avg1 + avg2) / 2, 2);