linq中的“Where”子句使用DateTime进行sql查询?

时间:2017-07-24 20:17:25

标签: c# linq datetime

我正在尝试在c#中运行包含Domain,LastUsed和FreqInHours列的表的查询。

我只想返回我需要抓取的所有域。我通过检查它们上次抓取的日期时间(LastUsed)以及它们应该被抓取的频率(例如每6小时)来找到它。如果当前日期/时间 - 上次抓取的时间大于我想要返回该域的频率。

这是我写的当前查询:

var query = (from c in context.SitemapFreqs
             where (DateTime.Now - c.LastUsed).TotalHours > c.Freq
             select c.domain);

以下是我的例外情况:

  

LINQ to Entities无法识别方法'System.DateTime?   ToDateTime(System.Object)'方法,并且此方法无法转换为商店表达式。

任何帮助都会非常感激。

3 个答案:

答案 0 :(得分:3)

您可以使用DbFunctions类和方法DiffHours

以下是一个例子:

var query = (from c in context.SitemapFreqs
             where DbFunctions.DiffHours(DateTime.Now,c.LastUsed) > c.Freq
             select c.domain);

这是documentation。希望它有所帮助。

答案 1 :(得分:0)

复杂的DateTime东西对于Linq2SQL来说有点多处理。

如果数据量相对较小,请先将其全部加载到内存中:

var query = (from c in context.SitemapFreqs.ToList()
             where (DateTime.Now - c.LastUsed).TotalHours > c.Freq
             select c.domain);

如果数据量较大,您可以使用DbFunctions,或自己提供查询。

context.SitemapFreqs.SqlQuery("SELECT * from SitemapFreqs WHERE DATEDIFF('hour', GETDATE(), LastUsed) > Freq")

如果您确保查询返回SitemapFreqs对象所需的列,它将像对待其他任何内容一样映射对象。

答案 2 :(得分:0)

看起来您的c.LastUsed属性可以为空。您可以使用c.LastUsed.Value属性减去可为空的DateTimes,但是您应该知道如果它为null,则会抛出异常,因为您无法减去DateTime - null。我相信你有两个选择:

  1. 通过删除?将类中的属性LastUsed更改为不可为空的DateTime。
  2. 在类中创建一个方法,用于确定DateTime? LastUsed是否等于null。如果是,则返回LINQ查询将忽略该值的内容。 (I.E:设置LastUsed的值= DateTime.Now,以便LINQ查询返回0)。
  3. 希望这有帮助。