0

我有一个 LINQ 查询。在那我需要做一些计算。一切都很好,除非在任一条件中找到空值,然后简单地为整个条件返回空值。谁能告诉我即使在条件中找到了一个空值,我怎么能返回一些值。

代码

var model = 
   (from q in db.Porders
    select new porders()
    {
        Id = q.Id,
        DetCount = (from amtdet in db.PoDetails 
                    where amtdet.PoId == q.Id 
                    select amtdet.Id).Count(),
        Amount = (from amtpord in db.Porders 
                  where amtpord.Id == q.Id 
                  select amtpord.Freight + amtpord.Misc - amtpord.Discount
                 ).FirstOrDefault() +
                  (from amtdet in db.PoDetails 
                   where amtdet.PoId == q.Id 
                   select amtdet.Copies * amtdet.EstUnitPrice
                  ).Sum()
     }).ToList();
4

3 回答 3

0

我认为该DefaultIfEmpty()方法将是这里的解决方案

var model =
    from q in db.Porders
    select new porders()
    {
        DetCount = 
            db.PoDetails.Count(amtdet => amtdet.PoId == q.Id),
        Amount = 
            (from amtpord in db.Porders
            where amtpord.Id == q.Id
            select amtpord.Freight + amtpord.Misc - amtpord.Discount)
            .DefaultIfEmpty().First()
            +
            (from amtdet in db.PoDetails
            where amtdet.PoId == q.Id
            select amtdet.Copies * amtdet.EstUnitPrice)
            .DefaultIfEmpty().Sum()
    }
于 2013-01-29T09:49:51.157 回答
0

尝试column ?? 0在可空列或结果上应用合并运算符FirstOrDefault(对于不满足条件的情况)。Linq to entity 会将此运算符转换为 SQL:

CASE WHEN Column IS NOT NULL THEN Column ELSE 0 END

它看起来像:

var model = 
   (from q in db.Porders
    select new porders()
    {
        Id = q.Id,
        Amount = (from amtpord in db.Porders 
                  where amtpord.Id == q.Id 
                  select amtpord.Freight ?? 0 + amtpord.Misc ?? 0 - amtpord.Discount ?? 0
                 ).FirstOrDefault() ?? 0 +
                  (from amtdet in db.PoDetails 
                   where amtdet.PoId == q.Id 
                   select amtdet.Copies ?? 0 * amtdet.EstUnitPrice ?? 0
                  ).Sum() ?? 0
     }).ToList();
于 2013-01-29T12:35:50.963 回答
0

首先让我假设有一个导航属性Porder.Details。接下来,为什么Porder在子查询中选择相同的?在我看来,您的查询可以简化为

from q in db.Porders
    select new porders()
    {
        Id = q.Id,
        DetCount = q.Details.Count(),
        Amount = q.Freight + q.Misc - q.Discount
               + q.PoDetails.Select( d => d.Copies * d.EstUnitPrice)
                  .DefaultIfEmpty().Sum()
    }

如果没有这样的导航属性,强烈建议创建一个。如果出于某种原因您不能或不想这样做,您应该在主查询 ( db.Porders.GroupJoin(db.PoDetails...)) 中对详细记录进行分组连接。

如果空值是由 引起的FreightMisc或者Discount可以为空,请使用??operator: q.Freight ?? 0

于 2013-01-29T13:20:51.977 回答