我有一个LINQ实体框架查询,它返回如下内容:
{Start: 1/1/2000T18:00:00, FirstName: John, LastName: Doe},
{Start: 1/1/2000T18:00:00, FirstName: Bob, LastName: Doe},
{Start: 1/1/2000T18:00:00, FirstName: Jack, LastName: Doe},
{Start: 1/1/2000T22:00:00, FirstName: John, LastName: Doe},
{Start: 1/1/2000T22:00:00, FirstName: Bob, LastName: Doe},
{Start: 1/1/2000T22:00:00, FirstName: Jack, LastName: Doe},
{Start: 2/1/2000T10:00:00, FirstName: John, LastName: Doe},
{Start: 2/1/2000T10:00:00, FirstName: Bob, LastName: Doe},
{Start: 2/1/2000T10:00:00, FirstName: Jack, LastName: Doe},
{Start: 2/1/2000T14:00:00, FirstName: John, LastName: Doe},
{Start: 2/1/2000T14:00:00, FirstName: Bob, LastName: Doe},
{Start: 2/1/2000T14:00:00, FirstName: Jack, LastName: Doe},
例如,人们在不同日子和不同时间的转变。
我想创建一个对象,其中班次分为几天和几小时,如下所示:
1/1/2000:
[
18:00:00:
[
{FirstName: John, LastName: Doe},
{FirstName: Bob, LastName: Doe},
{FirstName: Jack, LastName: Doe}
]
]
等...
使用LINQ to实体是否有方便的方法?
谢谢!
答案 0 :(得分:3)
您可以使用“分组依据”按多个属性进行分组,但首先需要提取“开始”的日期和时间部分。您可以按日期分组,然后按时间分组,或者语法更简单的方法是按两者分组,然后按时间对内部集合进行分组:
var x = from shift in Shifts
let date = EntityFunctions.TruncateTime(shift.Start)
let time = EntityFunctions.CreateTime(shift.Start.Hour, shift.Start.Minute, shift.Start.Second)
group shift by new { date, time } into groupedByDate
select new
{
Date = groupedByDate.Key.date,
ShiftsByTime = from g in groupedByDate group g by groupedByDate.Key.time
};
如果您不关心层次结构,也可以按{date,time}对进行分组:
var x = from shift in Shifts
let date = EntityFunctions.TruncateTime(shift.Start)
let time = EntityFunctions.CreateTime(shift.Start.Hour, shift.Start.Minute, shift.Start.Second)
group shift by new {date, time};
这是一个比上面第一个更详细但语义相同的查询。我检查了生成的SQL,它或多或少等价:
var x = from shift in Shifts
let date = EntityFunctions.TruncateTime(shift.Start)
group shift by date into groupedByDate
select new
{
Date = groupedByDate.Key,
ShiftsByTime = from g in groupedByDate
let time = EntityFunctions.CreateTime(g.Start.Hour, g.Start.Minute, g.Start.Second)
group g by time
};
答案 1 :(得分:0)
尝试使用.Select和.GroupBy像这样:
var res = list.Select(x => new
{
Person = x,
Date = x.Start.Date,
Time = x.Start.TimeOfDay
})
.GroupBy(x => x.Date)
.Select(personGroupByDate => new
{
Date = personGroupByDate.Key,
Persons = personGroupByDate
.Select(x => x.Person)
.GroupBy(x => x.Time)
.Select(person => new
{
FirstName = person.FirstName,
LastName = person.LastName
}).ToList()
}).ToList()
答案 2 :(得分:0)
您需要使用GroupBy来嵌套结果......
我发布了我的整个测试应用程序用于测试目的
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Web.Script.Serialization;
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
var objs = new Shift[] {
new Shift {Start= DateTime.Parse("1/1/2000 18:00:00"), FirstName= "John", LastName= "Doe"},
new Shift {Start= DateTime.Parse("1/1/2000 18:00:00"), FirstName= "Bob", LastName= "Doe"},
new Shift {Start= DateTime.Parse("1/1/2000 18:00:00"), FirstName= "Jack", LastName= "Doe"},
new Shift {Start= DateTime.Parse("1/1/2000 22:00:00"), FirstName= "John", LastName= "Doe"},
new Shift {Start= DateTime.Parse("1/1/2000 22:00:00"), FirstName= "Bob", LastName= "Doe"},
new Shift {Start= DateTime.Parse("1/1/2000 22:00:00"), FirstName= "Jack", LastName= "Doe"},
new Shift {Start= DateTime.Parse("2/1/2000 10:00:00"), FirstName= "John", LastName= "Doe"},
new Shift {Start= DateTime.Parse("2/1/2000 10:00:00"), FirstName= "Bob", LastName= "Doe"},
new Shift {Start= DateTime.Parse("2/1/2000 10:00:00"), FirstName= "Jack", LastName= "Doe"},
new Shift {Start= DateTime.Parse("2/1/2000 14:00:00"), FirstName= "John", LastName= "Doe"},
new Shift {Start= DateTime.Parse("2/1/2000 14:00:00"), FirstName= "Bob", LastName= "Doe"},
new Shift {Start= DateTime.Parse("2/1/2000 14:00:00"), FirstName= "Jack", LastName= "Doe"}
};
var dates = objs
.GroupBy(i => i.Start.Date)
.Select(i => new
{
Date = i.Key,
Times = i.GroupBy(s => s.Start.TimeOfDay).Select(s => new
{
Time = s.Key,
People = s.Select(ss => new { ss.FirstName, ss.LastName })
})
});
Console.ReadLine();
}
}
class Shift
{
public DateTime Start { get; set; }
public string FirstName { get; set; }
public string LastName { get; set; }
}
}