While working with Entity Framework SQL developers sometimes get struck on how to use group by clause with the sum, count min, and max, etc.We will use different types of an aggregate functions, and group by clause, to show the example.
Now let’s understand with an example, that we are going to create a table, first for ProductSales includes ProductName,ProductCategory, StoreCountry, SaleAmount, and OrderDate.
ProductSales Table
Id | ProductName | StoreCountry | SaleAmount | ProductCategory | OrderDate |
---|---|---|---|---|---|
1 | TVs | India | 2000 | Electronics | 3/29/2022 13:47 |
2 | Harry Potter | USA | 1500 | Books | 3/30/2022 13:47 |
3 | Tanis | UK | 1200 | Sports | 4/15/2022 13:47 |
4 | Jeans | India | 3000 | Clothing | 4/15/2022 13:47 |
5 | Ball | UK | 2200 | Sports | 4/16/2022 13:47 |
6 | Cap | USA | 800 | Clothing | 4/17/2022 13:47 |
7 | Keyboard | India | 600 | Computers | 4/20/2022 13:47 |
8 | Top | USA | 1400 | Clothing | 4/22/2022 13:47 |
9 | Bat | India | 1600 | Sports | 5/11/2022 13:47 |
10 | Laptop | UK | 900 | Computers | 5/12/2022 13:47 |
11 | Refrigerators | UK | 700 | Electronics | 5/13/2022 13:47 |
12 | Alice’s Adventures | India | 600 | Books | 5/16/2022 13:47 |
13 | T-shirt | USA | 550 | Clothing | 5/18/2022 13:47 |
14 | Refrigerators | India | 780 | Electronics | 5/21/2022 13:47 |
I want to calculate the total sales amount generated by ProductCategory. We can achieve this by using the 'group by' clause. To do it manually, we would take each Electronics record and add up their sale amount, then do the same for Books records. Essentially, we first group the records by ProductCategory and then sum the saleamount column within each group, which is why we use the 'group by' clause.
So, the query groups the ProductSales collection by ProductCategory and calculates the total sales amount for each product category. The result is stored in the sales variable as an enumerable collection of anonymous objects with ProductCategory and TotalSale properties.
Sql Query:
Select ProductCategory, SUM(SaleAmount) as TotalSale from ProductSales Group by ProductCategory
Linq Query:
var sales = from r in ProductSales group r by r.ProductCategory into gp select new {
ProductCategory = gp.Key, TotalSale = gp.Sum(a => a.SaleAmount)
};
Output:
ProductCategory | SaleAmount |
---|---|
Books | 2100 |
Clothing | 5750 |
Computers | 1500 |
Electronics | 3480 |
Sports | 5000 |
Let's consider another example where we use 'group by' with multiple columns. Now, we're not only grouping by ProductCategory but also by the store's Country. For instance, we want to know the total sales generated for each product category—Electronics, Books, Clothing, Computers, and Sports—in the USA. This means we're grouping by both the ProductCategory and Country columns. Essentially, we're first grouping the total sales by country and then further by ProductCategory.
The query groups the ProductSales list by a combination of StoreCountry and ProductCategory, and calculates the total sales amount for each unique combination. The result is stored in the sales variable as an enumerable collection of anonymous objects with StoreCountry, ProductCategory, and TotalSale properties.
Sql Query:
Select StoreCountry, ProductCategory, SUM(SaleAmount) as TotalSale from ProductSales Group by StoreCountry, ProductCategory
Linq Query:
var sales = from r in ProductSales group r by new {
r.StoreCountry, r.ProductCategory
}
into gp select new {
StoreCountr = gp.Key.StoreCountry, ProductCategory = gp.Key.ProductCategory, TotalSale = gp.Sum(a => a.SaleAmount)
};
Output:
StoreCountry | ProductCategory | TotalSale |
---|---|---|
India | Books | 600 |
USA | Books | 1500 |
India | Clothing | 3000 |
USA | Clothing | 2750 |
India | Computers | 600 |
UK | Computers | 900 |
India | Electronics | 2780 |
UK | Electronics | 700 |
India | Sports | 1600 |
UK | Sports | 3400 |
Let's illustrate with an example. We're displaying the total sales by country and ProductCategory, and we also want to include the total number of orders. To find the total number of orders, we can use the Count() function. Looking at the ProductSales table, we have 14 records. Now, we'll determine the total number of orders within the ProductSales table, and we'll use the 'order by' clause along with 'group by'.
The below query groups the ProductSales list by a combination of StoreCountry and ProductCategory, calculates the total sales amount and the total number of orders for each group, and then sorts the result by the TotalSales property in ascending order.
The result is stored in the sales variable as an enumerable collection of anonymous objects with StoreCountry, ProductCategory, TotalSales, and TotalOrder properties.
Sql Query:
Select StoreCountry, ProductCategory, SUM(SaleAmount) as TotalSales,COUNT(Id) as TotalOrder from ProductSales group by StoreCountry, ProductCategory order by TotalSales
Linq Query:
var sales = (from r in ProductSales group r by new {
r.StoreCountry, r.ProductCategory
}
into gp select new {
StoreCountry = gp.Key.StoreCountry, ProductCategory = gp.Key.ProductCategory, TotalSales = gp.Sum(item => item.SaleAmount), TotalOrder = gp.Count()
}).OrderBy(a => a.TotalSales);
Output:
StoreCountry | ProductCategory | TotalSales | TotalOrder |
---|---|---|---|
India | Books | 600 | 1 |
India | Computers | 600 | 1 |
UK | Electronics | 700 | 1 |
UK | Computers | 900 | 1 |
USA | Books | 1500 | 1 |
India | Sports | 1600 | 1 |
USA | Clothing | 2750 | 3 |
India | Electronics | 2780 | 2 |
India | Clothing | 3000 | 1 |
UK | Sports | 3400 | 2 |
Now, suppose we want to filter the output result to only include the ProductSales for the Books ProductCategory. To filter the records, we can use the 'where' clause, specifying that the ProductCategory is equal to 'Books'.
So, this query is similar to the above one, but it includes an additional filter to only consider records where the ProductCategory is "Books". The result is stored in the sales variable as an enumerable collection of anonymous objects with StoreCountry, ProductCategory, TotalSales, and TotalOrder properties, sorted by TotalSales in ascending order.
Sql Query:
Select StoreCountry, ProductCategory, SUM(SaleAmount) as TotalSales,COUNT(Id) as TotalOrder from ProductSales where ProductCategory='Books' group by StoreCountry, ProductCategory
Linq Query:
var sales = (from r in ProductSales where r.ProductCategory == "Books"
group r by new {
r.StoreCountry, r.ProductCategory
}
into gp select new {
StoreCountry = gp.Key.StoreCountry, ProductCategory = gp.Key.ProductCategory, TotalSales = gp.Sum(item => item.SaleAmount), TotalOrder = gp.Count()
}).OrderBy(a => a.TotalSales);
Output:
StoreCountry | ProductCategory | TotalSales | TotalOrder |
---|---|---|---|
India | Books | 600 | 1 |
USA | Books | 1500 | 1 |
Lets’ say, I want the max product sales that we are generating by StoreCountry.
Sql Query:
Select ProductCategory, Max(SaleAmount) as TotalSales from ProductSales Group by ProductCategory
Linq Query:
var sales = (from r in ProductSales group r by r.ProductCategory into gp select new {
ProductCategory = gp.Key, TotalSales = gp.Max(item => item.SaleAmount),
});
Output:
ProductCategory | TotalSales |
---|---|
Books | 1500 |
Clothing | 3000 |
Computers | 900 |
Electronics | 2000 |
Sports | 2200 |
Lets’ say, I want the min product sales that we are generating by StoreCountry.
Sql Query:
Select ProductCategory, MIN(SaleAmount) as TotalSales from ProductSales Group by ProductCategory
Linq Query:
var sales = (from r in ProductSales group r by r.ProductCategory into gp select new {
ProductCategory = gp.Key, TotalSales = gp.Min(item => item.SaleAmount),
});
Output:
ProductCategory | TotalSales |
---|---|
Books | 600 |
Clothing | 550 |
Computers | 600 |
Electronics | 700 |
Sports | 1200 |
Below is the table script which has some dummy data and you can get the SQL table script for your testing.
CREATE TABLE [dbo].[productsales]
We used to open an association with the information base, make a DataSet to get or present the information to the data set, convert information from the DataSet to .NET items or the other way around to apply business rules. This was an unwieldy and mistake inclined process. Microsoft has given a system called Element Framework to robotize every one of these information base related exercises for your application.
Substance Framework is an open-source ORM system for .NET applications upheld by Microsoft. It empowers engineers to work with information utilizing objects of space explicit classes without zeroing in on the hidden data set tables and segments where this information is put away. With the Entity Framework, engineers can work at a more elevated level of deliberation when they manage information, and can make and keep up with information situated applications with less code contrasted and customary applications.