IGrouping avoiding anonymous types

490 Views Asked by At

I would like to know how to group data avoiding anonymous types, because the keys may be one, two.. according to customer selection.

Example:

We have a class

public class Customer
{
    public string Name { get; set; }

    public int Age { get; set; }

    public string Location { get; set; }

    public char Genre { get; set; }
}

And through a checked list box, you may select parameters to group data, where the options would be:

  • Name
  • Age
  • Location
  • Genre

So we may have between 1 and 4 keys to group data.

I want to avoid a switch case or multiple if statements to get the correct IGrouping data.

I want to avoid:

 public IGrouping<object,Customer> GetGroups(IEnumerable<Customer> data)
 {
    if("Name is selected")
    {
        return data.GroupBy(e => e.Name);
    }
    if("Name and Age are selected")
    {
        return data.GroupBy(e => new { e.Name, e.Age });
    }
}
2

There are 2 best solutions below

0
Grigoryants Artem On BEST ANSWER

Not sure if this is something you are looking for, but might be helpful:

return data.GroupBy(g =>
  new {
    Name = includeName ? g.Name : null,
    Age = includeAge ? g.Age : null,
    ... 
  });
0
madoxdev On

This one works, it's a bit cheating, you just make sure the grouping key have proper values as per what you want your grouping to become. Below works, because if you don't want to group by a given property, you just set a default (same for every item) value.

    bool groupByName = false;
    bool groupByAge = false;
    bool groupByLocation = false;
    bool groupByGenre = true;
    
    var result = from x in items
                 group x by new { 
                                    Name = (!groupByName ? "" : x.Name), 
                                    Age = (!groupByAge ? 0 : x.Age),
                                    Location = (!groupByLocation ? "" : x.Location),
                                    Genre = (!groupByGenre ? ' ' : x.Genre)
                                } 
                                    into g
                 select g;