LINQ group by Clause
The group-by clause is used to group items using a specified key. The group-by clause can be inserted between a from clause and a select clause or you can put a group-by clause as the final clause of a query expression. The basic structure of a group-by clause is:
group item by key into groupVar
The group-by clause starts with the group contextual keyword followed by the item to be grouped. This is then followed by the bycontextual keyword. After it is the key which determines the criteria or how the items from the data source will be grouped. For example, you can indicate the city as the key to group every item by their respective cities. Next is the into keyword which specifies that the item will be placed in a separate collection(groupVar) that represents a group. The groupVar has a type of System.Linq.IGrouping<TKey, TElement> which uncovered the Key property of type TKey and contains gathered components of type TElement.
As for an example, say you want to group some players into different teams. Example 1 first declares a simple class named Player (lines 6-10) which has properties Name, and Team.
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
public class Player
{
public string Name { get; set; }
public string Team { get; set; }
}
public class Program
{
public static void Main()
{
List<Player> players = new List<Player>
{
new Player { Name = "Johnny", Team= "Red Team" },
new Player { Name = "Ross", Team = "Blue Team" },
new Player { Name = "Eric", Team = "Black Team" },
new Player { Name = "Josh", Team = "White Team" },
new Player { Name = "Mandy", Team = "Blue Team" },
new Player { Name = "Flora", Team = "White Team" },
new Player { Name = "Garry", Team = "Red Team" },
new Player { Name = "Joseph", Team = "Blue Team"},
new Player { Name = "Murray", Team = "Black Team"},
new Player { Name = "Henry", Team = "Black Team"},
new Player { Name = "Watson", Team = "Red Team"},
new Player { Name = "Linda", Team = "White Team"}
};
var groups = from p in players
group p by p.Team into g
select new { GroupName = g.Key, Members = g };
foreach (var g in groups)
{
Console.WriteLine("Members of {0}", g.GroupName);
foreach (var member in g.Members)
{
Console.WriteLine("---{0}", member.Name);
}
}
}
}
Example 1
Members of Red Team ---Johnny ---Garry ---Watson Members of Blue Team ---Ross ---Mandy ---Joseph Members of Black Team ---Eric ---Murray ---Henry Members of White Team ---Josh ---Flora ---Linda
We created a list of players (line 16-30) and assign each player their own team. Our goal is to group the players based on the team they are assigned to. The inquiry articulation in lines 32-34 utilizes a group-by clause(line 33) to assemble every player by taking a gander at their Teamproperty. Every player with comparable Team esteems will be grouped together into an IGrouping<string, Player> accumulation. Since we used Team as the key which is of type string, the kind of the Key property will be of type string as well and its substance are of type Player which speaks to each protest included to the gathering. The select clause(line 34) then ventures the outcome utilizing an unknown sort with the Key of each gathered allocated to the GroupName property and every one of the things in the gathering is doled out to the Membersproperty.
Lines 36-44 executes the query using a foreach loop. We need to use a nested foreach loop. The first foreach loop will loop through every group and print the name of the group. We used the GroupName property which uses the Key property of every IGroupingobjects from the query result. Inside it, another foreach loop will then enumerate every item included in the group. Remember that we assigned the group itself in the Members property during the projection in the select clause of the query statement. We used the Members property as the source in the inner foreach loop to iterate through each member of the group.
Ending Query Expressions with group-by Clause
You can also use the group-by statement to end a query expression. Remember that a query expression can only be ended by either a select clause or a group-by clause. The following is an example of a query expression with a group-by clause at its end.
var groups = from p in players
group p by p.Team;
foreach (var g in groups)
{
Console.WriteLine("Members of {0}", g.Key);
foreach (var member in g)
{
Console.WriteLine("---{0}", member.Name);
}
}
Figure 1
The query expression above produces the same output as Example 1. You will notice that we don’t need to assign every player into a group variable. The resulting type of the query result is an IEnumerable<IGrouping<string, Player>> interface which means that it is a collection of groups with a string key and contains Player objects.
Inside the first foreach loop, we utilized the Key property of each gathering which contains the name of each gathering since we used Teamproperty as the key in the group-by clause. The settled loop essentially utilizes the real gathering as the information source to emphasize through each Player contained in that gathering. One thing to note about group-by clause, any range variable before the group-by clause will be out of extension after the group-by clause.
The GroupBy() Method
A gathering by provision is made an interpretation of into a call to the GroupBy() method which is additionally an expansion strategy for the IEnumerable<T> interface. The accompanying example demonstrates how you can compose the inquiry in Figure 2 utilizing the GroupBy() method.
var groups = players.GroupBy(p => p.Team);
The GroupBy() method accepts a lambda expression that has one parameter which will hold every value from the data source and returns the key that will be used for grouping.
The query in Example 1 can be done by following the call to the GroupBy() method with a call to the Select() method to project the data.
var groups = players.GroupBy(p => p.Team)
.Select(g => new { GroupName = g.Key, Members = g });
The Select() method uses every group yielded by the GroupBy() method and uses projection to create a much clearer set of properties.