Linq groupby on two properties

Say I have a list of orders. Each order has a link to the customer and the product they bought. For instance:

class Orders { public int CustomerId {get;set;} public int ProductId {get;set;} } 

I want to group all orders in which different customers have the same set of products in one group.

  • Customer 1 - Product 1 and 2
  • Customer 2 - Product 1 & 2 & 3
  • Customer 3 - Product 1 and 2
  • Customer 4 - Product 3 & 4 & 5

In this case, orders for customer 1 and 3 will be in the same group, and orders for 2 and 4 will have their own group.

Can this be done with LINQ? I started by trying to group by CustomerId , but I got lost on how to proceed from there.

+5
source share
1 answer

Availability:

 List<Orders> orders = new List<Orders>(); orders.Add(new Orders { CustomerId = 1, ProductId = 1 }); orders.Add(new Orders { CustomerId = 1, ProductId = 2 }); orders.Add(new Orders { CustomerId = 2, ProductId = 2 }); orders.Add(new Orders { CustomerId = 2, ProductId = 3 }); orders.Add(new Orders { CustomerId = 3, ProductId = 1 }); orders.Add(new Orders { CustomerId = 3, ProductId = 2 }); orders.Add(new Orders { CustomerId = 4, ProductId = 3 }); orders.Add(new Orders { CustomerId = 4, ProductId = 4 }); 

LINQ query:

  var groupedCustomers = orders.GroupBy(i => i.CustomerId) .Select(i => new { CUSTOMER = i.Key, ORDERS = i.Select(j => j.ProductId) .OrderBy(j => j) //.Distinct() to ignore duplicate orders .ToArray() }) .ToList(); var result = groupedCustomers.GroupBy(i => i.ORDERS, new IntArrayComparer()).ToList(); 

And here is the comparator.

  public class IntArrayComparer : IEqualityComparer<int[]> { public bool Equals(int[] x, int[] y) { return x.SequenceEqual(y); } public int GetHashCode(int[] obj) { return base.GetHashCode(); } } 

EDIT: If you are looking for the smart GetHashCode function, you can try something like this:

 public int GetHashCode(int[] obj) { return string.Join(",", obj.Select(i => i.ToString())).GetHashCode(); } 
+7
source

All Articles