Grouping is one of the more powerful features of LINQ.

Assume you had the following data:

Kingdom Name Legs
Animal Dog 4
Animal Cat 4
Animal Horse 4
Animal Millipede 3000
Animal Centipede 3000
Animal Octopus 8
Animal Squid 8
Plant Rose 0
Plant Cabbage 0
Plant Kale 0

This would be contained in a collection like this in C#

var livingThings = new List<LivingThing>();
livingThings.AddRange(new[] {
    new LivingThing()  {Kingdom = "Animal", Name = "Dog", Legs = 4},
    new LivingThing()  {Kingdom = "Animal", Name = "Cat", Legs = 4},
    new LivingThing()  {Kingdom = "Animal", Name = "Horse", Legs = 4},
    new LivingThing()  {Kingdom = "Animal", Name = "Millipede", Legs = 3_000},
    new LivingThing()  {Kingdom = "Animal", Name = "Centipede", Legs = 3_000},
    new LivingThing()  {Kingdom = "Animal", Name = "Octopus", Legs = 8},
    new LivingThing()  {Kingdom = "Animal", Name = "Squid", Legs = 8},
    new LivingThing()  {Kingdom = "Plant", Name = "Rose", Legs = 0},
    new LivingThing()  {Kingdom = "Plant", Name = "Cabbage", Legs = 0},
    new LivingThing()  {Kingdom = "Plant", Name = "Kale", Legs = 0}
});

And like this in VB.NET

Dim livingThings As New List(Of LivingThing)
livingThings.AddRange(New LivingThing() {
    New LivingThing() With {.Kingdon = "Animal", .Name = "Dog", .Legs = 4},
    New LivingThing() With {.Kingdon = "Animal", .Name = "Cat", .Legs = 4},
    New LivingThing() With {.Kingdon = "Animal", .Name = "Horse", .Legs = 4},
    New LivingThing() With {.Kingdon = "Animal", .Name = "Millipede", .Legs = 3_000},
    New LivingThing() With {.Kingdon = "Animal", .Name = "Centipede", .Legs = 3_000},
    New LivingThing() With {.Kingdon = "Animal", .Name = "Octopus", .Legs = 8},
    New LivingThing() With {.Kingdon = "Animal", .Name = "Squid", .Legs = 8},
    New LivingThing() With {.Kingdon = "Plant", .Name = "Rose", .Legs = 0},
    New LivingThing() With {.Kingdon = "Plant", .Name = "Cabbage", .Legs = 0},
    New LivingThing() With {.Kingdon = "Plant", .Name = "Kale", .Legs = 0}
})

If we wanted to know, what are the distinct collections of Kingdom and Leg in the collection we would do it like this:

var distinctElements = livingThings.DistinctBy(t => new { t.Kingdom, t.Legs });
foreach (var element in distinctElements)
{
    Console.WriteLine($"Kingdom: {element.Kingdom}; Legs: {element.Legs}");
}

This would print the following:

Kingdom: Animal; Legs: 4
Kingdom: Animal; Legs: 3000
Kingdom: Animal; Legs: 8
Kingdom: Plant; Legs: 0

The same code is like this in VB.NET

Dim distinctElements = livingThings.DistinctBy(Function(t) New With {t.Kingdom, t.Legs})
For Each element In distinctElements
    Console.WriteLine($"Kingdom: {element.Kingdom}; Legs: {element.Legs}")
Next

This code, however, prints the following:

Kingdom: Animal; Legs: 4
Kingdom: Animal; Legs: 4
Kingdom: Animal; Legs: 4
Kingdom: Animal; Legs: 3000
Kingdom: Animal; Legs: 3000
Kingdom: Animal; Legs: 8
Kingdom: Animal; Legs: 8
Kingdom: Plant; Legs: 0
Kingdom: Plant; Legs: 0
Kingdom: Plant; Legs: 0

Notice it not only repeats elements, it prints as many elements that are in the original collection!

The problem here is that VB.NET behaves differently from C# - it has slightly different rules for determining how anonymous types are Equal

To get VB.NET to do what we want, we need to make use of the Key keyword.

The code should be updated to look like this:

Dim distinctElements = livingThings.DistinctBy(Function(t) New With {Key t.Kingdom, Key t.Legs})
For Each element In distinctElements
    Console.WriteLine($"Kingdom: {element.Kingdom}; Legs: {element.Legs}")
Next

The different bits are here:

This now prints what we expect.

Kingdom: Animal; Legs: 4
Kingdom: Animal; Legs: 3000
Kingdom: Animal; Legs: 8
Kingdom: Plant; Legs: 0

The code is in my Github.

Happy hacking!