LINQ GroupBy DateTime 困境
我有以下代码:
public IDictionary<string, int> GetCountByDate(DateTime fromDate, DateTime toDate)
{
var result = Database.Set<User>().Where(x => x.CreatedAt >= fromDate && x.CreatedAt <= toDate).GroupBy(x => new { x.CreatedAt.Year, x.CreatedAt.Month, x.CreatedAt.Day }).Select(x => new { Date = x.Key, Count = x.Count() });
return result.ToDictionary(x => new DateTime(x.Date.Year, x.Date.Month, x.Date.Day).ToShortDateString(), x => x.Count);
}
该代码工作得很好,但问题是 DateTime 在数据库中存储为 UTC。当我执行 GroupBy 操作时,我失去了时间部分。因此,如果我尝试使用以下命令将其转换回本地时间:
return result.ToDictionary(x => new DateTime(x.Date.Year, x.Date.Month, x.Date.Day).ToLocalTime().ToShortDateString(), x => x.Count);
它将基于不同的时间,因此不正确。该列必须保留日期时间。
有什么建议吗?
I have the following code:
public IDictionary<string, int> GetCountByDate(DateTime fromDate, DateTime toDate)
{
var result = Database.Set<User>().Where(x => x.CreatedAt >= fromDate && x.CreatedAt <= toDate).GroupBy(x => new { x.CreatedAt.Year, x.CreatedAt.Month, x.CreatedAt.Day }).Select(x => new { Date = x.Key, Count = x.Count() });
return result.ToDictionary(x => new DateTime(x.Date.Year, x.Date.Month, x.Date.Day).ToShortDateString(), x => x.Count);
}
This code works perfectly well but the problem is that the DateTime is stored as UTC in the database. The moment I do the GroupBy operation I lose the Time part. So if I tried to convert it back to loca time with the following:
return result.ToDictionary(x => new DateTime(x.Date.Year, x.Date.Month, x.Date.Day).ToLocalTime().ToShortDateString(), x => x.Count);
It would be based on a different time and therefore incorrect. The column has to stay DateTime.
Any suggestions?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
听起来真正的挑战是您需要翻译两次。首先,将您输入到方法中的本地日期时间(只有在本地的情况下您的问题才有意义)需要转换为 UTC 以进行查询。但是,在进行分组之前,您需要将 x.CreatedAt 转换为本地(换句话说,在服务器上)。这很棘手,但如果您在 System.Data.Objects.SqlClient 中使用 SqlFunctions 库,则可以使用。这就是它的样子。凌乱,我不知道它的性能如何,但它应该可以工作。
此时,字典对象中的日期值已经是本地时间,因此无需转换它们以进行演示。
It sounds like the real challenge is that you'll need to translate twice. First, taking the local DateTime you're feeding into the method (your question only makes sense if those are local) need to be translated into UTC for the query. But then you need to translate x.CreatedAt into local before you do your grouping—on the server, in other words. This is tricky, but works if you use the SqlFunctions library in System.Data.Objects.SqlClient. Here's what it'd look like. Messy and I don't know how performant it'd be, but it should work.
At that point, the date values in your dictionary object are already in local time, so no need to convert them for presentation.