Sum()在Entity Framework Query中返回null

Jon*_*ood 14 c# linq entity-framework

我有一个包含这些行的大型Entity Framework查询.

var programs = from p in Repository.Query<Program>()
               where p.OfficeId == CurrentOffice.Id
               let totalCharges = p.ProgramBillings.Where(b => b.Amount > 0 && b.DeletedDate == null).Select(b => b.Amount).Sum()
               let totalCredits = p.ProgramBillings.Where(b => b.Amount < 0 && b.DeletedDate == null).Select(b => -b.Amount).Sum()
               let billingBalance = (totalCharges - totalCredits)
Run Code Online (Sandbox Code Playgroud)

当我实现数据时,我收到以下错误:

转换为值类型'Decimal'失败,因为具体化值为null.结果类型的泛型参数或查询必须使用可空类型.

如果我按如下方式更改我的查询(添加了两个类型转换),则错误消失.

var programs = from p in Repository.Query<Program>()
               where p.OfficeId == CurrentOffice.Id
               let totalCharges = (decimal?)p.ProgramBillings.Where(b => b.Amount > 0 && b.DeletedDate == null).Select(b => b.Amount).Sum()
               let totalCredits = (decimal?)p.ProgramBillings.Where(b => b.Amount < 0 && b.DeletedDate == null).Select(b => -b.Amount).Sum()
               let billingBalance = (totalCharges - totalCredits)
Run Code Online (Sandbox Code Playgroud)

我不明白.ProgramBilling.Amount是一个不可为空的十进制.如果我将鼠标悬停在Sum()调用上,Intellisense会说它返回Decimal类型.然而额外的测试证实,在我的第二个版本,totalCharges并且totalCredits都设置为null,其中这些行ProgramBillings没有数据.

问题:

  1. 我理解Sum()为空集合返回0.在什么情况下这不是真的?

  2. 如果有时这不是真的,那么为什么当我将鼠标悬停在上面时Sum(),Intellisense会显示它返回的类型为Decimal而不是Decimal?看起来Intellisense和我有同样的理解.

编辑:

似乎一个简单的解决方法就是做类似的事情Sum() ?? 0m.但这是非法的,给我错误:

接线员'??' 不能应用于'decimal'和'decimal'类型的操作数

Ser*_*rvy 10

我知道Sum()为空集合返回0.在什么情况下这不是真的?

当您没有使用LINQ对象时,就像这里的情况一样.这里有一个查询提供程序,可以将此查询转换为SQL.SQL操作对其SUM运算符具有不同的语义.

如果有时候这不是真的,那么为什么当我将鼠标悬停在Sum()上时,Intellisense会显示它返回的类型为Decimal而不是Decimal?看起来Intellisense和我有同样的理解.

C#LINQ SUM运算符不返回可为空的值; 它需要具有非null值,但SQL SUM运算符具有不同的语义,它null在求和空集时返回,而不是0.null在C#需要非空值的上下文中提供值的事实是一切都在破坏的全部原因.如果这里的C#LINQ SUM运算符返回了一个null可以为空的值,那么可以只返回没有任何问题.

它是用于表示导致此错误的C#运算符和SQL运算符之间的差异.