在select子句中应用函数

时间:2015-05-12 10:53:29

标签: c# linq-to-sql

我有一个查询(longish with joins etc)和select子句中的某些字段(所有字段都是decimal?类型),我想在DB存储它们时返回null0。正确执行以下工作:

var q =
    from O in ....
    ....
    select new
    {
        ...
        Spot = O.Spot == 0 ? null : O.Spot,
        Moneyness = O.Strike / (O.Spot == 0 ? null : O.Spot),
        Volatility = O.Rate == 0 ? null : O.Rate
    };

但我更愿意在函数中封装0的检查。所以我试过

private static decimal? NullIfZero(decimal? obj)
{
    return  obj == 0 ? null : obj;
}

然后

var q =
    from O in ....
    ....
    select new
    {
        ...
        Spot = NullIfZero(O.Spot),
        Moneyness = O.Strike / NullIfZero(O.Spot),
        Volatility = NullIfZero(O.Rate)
    };

但现在我收到了错误:

  

类型'System.InvalidOperationException'的未处理异常   发生在System.Data.Linq.dll

中      

其他信息:无法翻译表达式   'NullIfZero(<> h__TransparentIdentifier0.O.Spot)'进入SQL并且可以   不要把它当作本地表达。

如果我尝试

,我不会收到错误
var q =
    from O in ....
    ....
    select new
    {
        ...
        Spot = NullIfZero(O.Spot),
        Moneyness = O.Strike / (O.Spot == 0 ? null : O.Spot),
        Volatility = NullIfZero(O.Rate)
    };

但是我看不出NullIfZero(O.Spot)(O.Spot == 0 ? null : O.Spot)之间的区别是什么,特别是在用作除数时它似乎只有效果。

1 个答案:

答案 0 :(得分:2)

第一个查询失败,因为L2S无法翻译函数调用NullIfZero。第二个查询有效,因为L2S可以评估本地函数,如果它们是查询中最后一个Select的一部分。这是EF现在所缺乏的非常好的功能。

解决方案:

  1. 内联功能。
  2. 从谓词构建器库中尝试AsExpandable