【问题标题】:Add date and time columns in where clause in Entity Framework 6在实体框架 6 的 where 子句中添加日期和时间列
【发布时间】:2020-01-14 22:39:25
【问题描述】:

我有一个 SQL Server 2016 事件表,其中事件日期和开始时间存储在不同的列中。我正在尝试编写一个查询来确定表中已经存在的DateTimes 列表中的哪一个,因此我需要在进行比较之前添加或组合EventDateStartTime 列,如下所示:

public List<DateTime> DoEventsExist(List<DateTime> dateBatch)
{
    try
    {
        DBContext.Events.Where(ce => dateBatch.Contains(ce.EventDate.Add(ce.StartTime));
    }
    catch (Exception ex)
    {
    }
}

但是,当然,这会给消息一个例外:

LINQ to Entities 无法识别方法 'System.DateTime Add(System.TimeSpan)' 方法,并且该方法无法转换为存储表达式。

在这种情况下,列分别是 DateTime 类型(因此 .NET 类型是 DateTimeTimeSpan),但我也想知道如果它们是两种DateTime2 类型,其中一种包含午夜的日期,另一种包含具有正确时间的不相关日期。

SqlFunctions.DateAdd 可能会起作用,但它会使我的代码与我不想要的 MS SQL Server 紧密耦合。

注意 有一个similar question,但它没有询问组合两个日期时间。此外,它并非特定于 EF 6,它的答案早于 EF 6,而且答案不起作用,因此整个问题对 SO 毫无用处。

【问题讨论】:

  • 你说“我相信这会给我一个错误”。这是否意味着您还没有尝试过?
  • 使用SqlFunctions.DateAdd?
  • @Rufus 是的,我没有尝试过这段代码。我知道它会给出一个错误,不知道错误的确切文本。
  • @NetMage - 这可能会起作用,除非它将我的数据层与 SQL Server 耦合。我看到了你的链接。也许是版本差异,但我什至无法使其工作。正如我所料,“LINQ to Entities 不支持'TotalSeconds'”。请参阅我在上面添加的注释。

标签: c# linq entity-framework-6


【解决方案1】:

鉴于您有一个日期时间值列表,这种查询方式确实无法将您带到您想去的地方。

按照您的建议,将其更改为 TVP。

您也可以按照建议将 TVP 传递给过程,但 TVP 也可以作为参数传递给即席 SQL 查询。

【讨论】:

  • 您能否详细说明“这种查询方式确实无法将您带到您想去的地方”?每个查询的 SQL Server 限制为 2100 个日期(我可能从未遇到过,但我将其分块)但是 [docs.microsoft.com/en-us/sql/relational-databases/tables/… 提到 TVP 最多只能执行 1000 行。因此,除非无法在查询中组合日期和时间,否则样式似乎还可以,这似乎是真的。
  • 您绝对可以在查询中结合日期和时间。查看 DATETIMEFROMPARTS 和相关函数。 (不知道从 EF 中使用它)但是您需要传递 TVP 或逐行调用查询(不好)。 TVP 最适合较少的行数。如果您真的需要性能,为什么不只是:a)截断临时表,b)在您的查询中,将所有值插入该表,然后 c)执行单个批量查询以获取结果?至少那时您可以正确索引所有涉及的表等。 (2100 个日期作为参数传递很多)。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-12-31
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多