Linq使用可空的datetime字段

时间:2012-09-25 15:06:49

标签: linq

我在使用以下内容时遇到LINQ问题(使用EF-4.3.1.0):

    DateTime? dtcollected = DateTime.TryParse(dateCollected, out dateVal) ? dateVal : (DateTime?)null;
    DateTime?  dtanalyzed =  DateTime.TryParse(dateanalyzed, out dateVal) ? dateVal : (DateTime?)null; 


     var doesexist = (from pw in dbContext.WtTbl                                      
                      where pw.CompanyId == 13
                      && pw.DateCollected == dtcollected
                      && pw.DateAnalyzed == dtanalyzed                                    
                      select pw).Any();

请注意,dateCollected作为字符串输入,因此我必须将其转换为可为空的DateTime。同样适用于日期分析。

我感到震惊的是我有一个13的companyId.dtcollected的空值。并且已经在表中进行了dtanalyzed的值,所以我希望doesexist返回true,但它返回false。

如果我发表评论

     var doesexist = (from pw in dbContext.WtTbl                                      
                      where pw.CompanyId == 13
                    //   && pw.DateCollected == dtcollected
                      && pw.DateAnalyzed == dtanalyzed                                    
                      select pw).Any();

或者说:

      var doesexist = (from pw in dbContext.WtTbl                                      
                      where pw.CompanyId == 13
                      && pw.DateCollected == null
                      && pw.DateAnalyzed == dtanalyzed                                    
                      select pw).Any();

然后我得到了一个真实的。为什么它无法理解dtcollected的空值? 难道我做错了什么。

1 个答案:

答案 0 :(得分:1)

在大多数数据库系统(绝对是SQL Server)中,如果比较的一方为null,则比较结果是未知的,因此不包括在结果集中(或者,对于所有意图和目的,false)

也就是说,您需要对变量执行null检查,如果参数为非null,则只检查数据库字段,如下所示:

var doesexist = (
    from pw in dbContext.WtTbl                                      
    where 
        pw.CompanyId == 13 && 
        (dtcollected == null || pw.DateCollected == dtcollected) &&
        (dtanalyzed == null || pw.DateAnalyzed == dtanalyzed)
    select pw).Any();

这大致翻译为:

declare @dtcollected date = null
declare @dtanalyzed date = null

select 
    * 
from 
    Table as t
where
    (@dtcollected is null or t.DateCollected = @dtcollected) and
    (@dtanalyzed is null or t.DateAnalyzed  = @dtanalyzed)