Awesome LINQ Features In .Net 6

Chunking

Chunking is a concept in which the sequence of elements are split into different portions of mentioned size.

Example

I have a list of string object which holds the list of cities.

var bigCities = new List<string>() { "New York", "London", "Mumbai", "Chicago", "Sydney", "Toronto" };

Now I want to split the object into parts with size of three.

Generally we end up writing a complicated LINQ query to do this step

int chunkSize = 3;
var chunkedOutput = bigCities.Select((x,i) => new { Index=i,value =x })
    .GroupBy(x=>x.Index/chunkSize).Select(x=>x.Select(m=>m.value));

The above query will return me the output where the result set will be split into two parts with size 3.

The same process can be done simply by using a method which is available in .NET 6.

var chunkedOutput = bigCities.Chunk(3);
public static System.Collections.Generic.IEnumerable<TSource[]> Chunk<TSource>(this System.Collections.Generic.IEnumerable<TSource> source, int size);

The Maximum of each chunk is Int32.

var bigCities = new List < string > () {
    "New York",
    "London",
    "Mumbai",
    "Chicago",
    "Sydney",
    "Toronto"
};
//In Previous Versions of Dotnet
int chunkSize = 3;
var chunkedOutput = bigCities.Select((x, i) => new {
    Index = i, value = x
}).GroupBy(x => x.Index / chunkSize).Select(x => x.Select(m => m.value));
//In .Net 6
var chunked = bigCities.Chunk(2);

Awesome Linq Features in dotNet

Getting Count without Enumeration

var bigCities = new List<string>() { "New York", "London", "Mumbai", "Chicago", "Sydney", "Toronto" }.AsEnumerable();
bigCities.Count();

In the above code, If I want to find the count of bigCities object by using Count() method, it will make an enumeration.

But in .Net6 we can achieve this without making an enumeration.

bigCities.TryGetNonEnumeratedCount(out int count);

By using this TryGetNonEnumeratedCount we can determine the number of elements in a sequence without forcing an Enumeration.

Below is the code for this TryGetNonEnumeratedCount() Method.

// Summary:
//     Attempts to determine the number of elements in a sequence without forcing an
//     enumeration.
//
// Parameters:
//   source:
//     A sequence that contains elements to be counted.
//
//   count:
//     When this method returns, contains the count of source if successful, or zero
//     if the method failed to determine the count.
//
// Type parameters:
//   TSource:
//     The type of the elements of source.
//
// Returns:
//     true if the count of source can be determined without enumeration; otherwise,
//     false.
public static bool TryGetNonEnumeratedCount < TSource > (this IEnumerable < TSource > source, out int count) {
    throw null;
}

Zipping

A sequence of tuples with elements taken from the first, second, and third sequences, in that order.

We are having three sequences as given below

var playerName = new string[] { "Dhoni", "Kohli", "Sachin", "Ganguly" };
var jerseryNumber = new int[] { 7, 18, 10, 99 };
var place = new string[] { "Ranchi", "Delhi", "Mumbai", "Kolkata" };

Now we are trying to Zip the three sequences by using Zip function.

IEnumerable<(string Player, int Jersey, string Birth)> zip = playerName.Zip(jerseryNumber, place);

The output will be as given below

Awesome Linq Features in dotNet

 // Summary:
 //     Produces a sequence of tuples with elements from the three specified sequences.
 //
 // Parameters:
 //   first:
 //     The first sequence to merge.
 //
 //   second:
 //     The second sequence to merge.
 //
 //   third:
 //     The third sequence to merge.
 //
 // Type parameters:
 //   TFirst:
 //     The type of the elements of the first input sequence.
 //
 //   TSecond:
 //     The type of the elements of the second input sequence.
 //
 //   TThird:
 //     The type of the elements of the third input sequence.
 //
 // Returns:
 //     A sequence of tuples with elements taken from the first, second, and third sequences,
 //     in that order.
 public static IEnumerable < (TFirst First, TSecond Second, TThird Third) > Zip < TFirst, TSecond, TThird > (this IEnumerable < TFirst > first, IEnumerable < TSecond > second, IEnumerable < TThird > third) {
     throw null;
 }

MinBy & MaxBy

MinBy and MaxBy are introduced by Microsoft for using these instead of orderBy and OrderByDescending in much simpler way.

Here is an example of how this works.

public class PlayerScore {
    public PlayerScore(string name, int score) {
        PlayerName = name;
        Score = score;
    }
    public string PlayerName {
        get;
        set;
    }
    public int Score {
        get;
        set;
    }
}
var playerScore = new [] {
    new PlayerScore("Dravid", 95),
        new PlayerScore("Sachin", 75),
        new PlayerScore("Dhoni", 100),
        new PlayerScore("Kohli", 35)
};

I have created an array of player scores. Now I need to find the lowest scored player and highest scored player.

Generally we write this kind of linq query to fetch the result.

var lowestScoredPlayer = playerScore.OrderBy(e => e.Score).First();
var highestScoredPlayer = playerScore.OrderByDescending(e => e.Score).First()

Here we end up writing two methods to perform the required operation. But in .Net 6 it got much simpler by using this MinBy and MaxBy

var lowestScored = playerScore.MinBy(e => e.Score);
var highestScored = playerScore.MaxBy(e => e.Score);

Writing the query as above will provide the desired result.

Take Accepting Range

var bigCities = new List<string>() { "New York", "London", "Mumbai", "Chicago", "Sydney", "Toronto" }.AsEnumerable();

If I want to skip the first two elements of the list and fetch the next two elements of the list we need to write the query as below.

var result = bigCities.Skip(2).Take(2);

Instead of writing two methods in same linq query, we can add range to Take Method and the same query can be written simply in .Net 6.

var result = bigCities.Take(2..4);

Awesome Linq Features in dotNet

if you want to fetch the last 2 elements of the list, we can use index of element and set the range as below

var lastTwo = bigCities.Take(^2..);

Awesome Linq Features in dotNet

Please post your comments on this Blog. Also attaching the solution below with all the queries written in it. Please install .Net 6 with VS2022 to access the solution.