LINQ GroupBy用于多列

时间:2017-12-01 03:51:50

标签: c# linq

我陷入逻辑分组。我有一个包含所有信息的模型,但我必须根据CustomerBuildingMapping

对信息进行分组
public class TicketsDataModel
{
    public string BuildingID { get; set; }
    public string Ticket { get; set; }
    public string Amount { get; set; }
    public string CustomerID { get; set; }
    public string BuildingName { get; set; }
}

当前数据

BuildingID | Ticket | Amount |CustomerID | BuildingName 
10         | 001    | 50     | 1         | JP Building
11         | 002    | 45     | 1         | Tiskon
52         | 452    | 35     | 2         | Lalit
65         | 568    | 78     | 2         | Tuilp
41         | 121    | 12     | 1         | BK Trp

-

public class CustomerBuildingMapping
{
    public long LeadID { get; set; }
    public string CustomerID { get; set; }
    public List<BuildingInfo> BuildingInfo{ get; set; }
}
public class BuildingInfo
{
    public string BuildingID { get; set; }
    public string TicketNumber { get; set; }
    public long Amount { get; set; }
    public string BuildingName { get; set; }
}

分组后的预期数据

LeadID 1001
CustomerID 1
BuildingInfo
               BuildingID | Ticket | Amount  | BuildingName 
               10         | 001    | 50      | JP Building
               11         | 002    | 45      | Tiskon
               41         | 121    | 12      | BK Trp
LeadID 1002
CustomerID 2
BuildingInfo
               BuildingID | Ticket | Amount  | BuildingName 
               52         | 452    | 35      | Lalit
               65         | 568    | 78      | Tulip

我已编写此代码,但无法按多列分组。

List<CustomerBuildingMapping> objCustomerBuildingMappingResult = objTicketsForTheDayInfo.TicketsForTheDay.GroupBy(l => l.CustomerID).Select(grp => new CustomerBuildingMapping
            {
                CustomerID = grp.Key,
                //BuildingInfo = grp.Select(l => l.BuildingID).ToList(),
            }).ToList();

2 个答案:

答案 0 :(得分:3)

您不需要按多列分组。根据示例数据,您只能按一个字段CustomerID进行分组。

var objCustomerBuildingMappingResult = objTicketsForTheDayInfo.TicketsForTheDay
.GroupBy(l => l.CustomerID)
.Select(grp => new CustomerBuildingMapping
        {
            CustomerID = grp.Key,
            LeadId = long.Parse(grp.Key) + 1000,
            BuildingInfo = grp.Select(l => new BuildingInfo {
                BuildingID = l.BuildingID,
                TicketNumber = l.Ticket,
                Amount = l.Amount,
                BuildingName = l.BuildingName
            }).ToList(),
        }).ToList();

答案 1 :(得分:0)

正如Nkosi指出的那样,在OP的例子中,因为LeadId是一个自动生成的代理键,所以除了单个键之外,不需要GroupBy字段(CustomerID),并创建一个函数来生成代理LeadId

但是,在更一般的情况下,如果需要为GroupBy构建复合键,则在旧版本的C#上都有Tuples System.Tuple}两种类型,与System.ValueTuple.GroupBy一起使用时,<#1}}在C#7及更高版本中制作好的瞬态分组密钥。这是因为Tuples在内部构建了元组实例的HashCode by combining the underlying Hashcodes of the contained types

对于较旧的System.Tuple,您需要处理丑陋的.ToDictionary属性:

Itemx

但是System.ValueTuple更具可读性(和性能):

var objCustomerBuildingMappingResult = objTicketsForTheDayInfo
        .TicketsForTheDay
        .GroupBy(l => Tuple.Create(l.CustomerID, l.BuildingID))
        .Select(grp => new CustomerBuildingMapping
        {
            CustomerID = grp.Key.Item1,
            BuildingId = grp.Key.Item2,
            // ...
        })
        .ToList();