День сто восьмой. #ЗаметкиНаПолях

LINQ. Продолжение

Основные примеры

1. Ключевые компоненты — Where, Select и Aggregate:

// Фильтрация списка (выбор овчарок из списка собак)

// API

var shepards = dogs.Where(dog => dog.Breed == DogBreed.Shepard);

// Запрос

var queryShepards = from dog in dogs

where dog.Breed == DogBreed.Shepard

select dog;



// Отображение списка объектов типа A в список объектов типа B

// API

var cats = dogs.Select(dog => dog.TurnIntoACat());

// Запрос

var queryCats = from dog in dogs

select dog.TurnIntoACat();



// Суммирование длин строк из набора

int sumOfStrings = strings.Aggregate(0, (s1, s2) => s1 + s2.Length);



2. Спрямление списка списков:

// Преобразование списка собачьих питомников в единый список собак из всех питомников

var allDogsFromKennels = kennels.SelectMany(kennel => kennel.Dogs);



3. Объединение/пересечение двух наборов с пользовательским блоком сравнения (используется объект, реализующий IEqualityComparer<T>, для сравнения объектов между собой):

// Получаем всех короткошёрстных собак из двух питомников

var shortHairedDogs = kennel1.Dogs.Union(kennel2.Dogs, new HairComparer());



public class HairComparer : IEqualityComparer<Dog> {…}



// Получаем волонтёров, работающих в обоих благотворительных обществах

var volunteers = humaneSociety1.Volunteers.Intersect(humaneSociety2.Volunteers, new VolunteerTimeComparer());



4. Упорядочение набора:

// Получаем пути движения, упорядоченные сначала по отсутствию платных участков, затем по времени в пути

var results = DirectionsProcessor.GetDirections(start, end)

.OrderBy(direction => direction.HasNoTolls)

.ThenBy(direction => direction.EstimatedTime);



5. А этот метод расширения использует отражение, чтобы вывести набор открытых свойств экземпляра, имеющих те же значения, что и у другого экземпляра:

public static class PropExtensions

{

public static IEnumerable<PropertyInfo> PublicEqualProps<T>(this T self, T to, params string[] ignore) where T : class

{

if (self == null || to == null)

return null;



// Выбирает свойства с одинаковыми значениями, не входящие в ignore, в набор свойств

var equalProps = from property in typeof(T).GetProperties(BindingFlags.Public | BindingFlags.Instance)

where !ignore.Contains(property.Name)

let selfValue = property.GetValue(self, null)

let toValue = property.GetValue(to, null)

where !Equals(selfValue, toValue)

select property;



return equalProps;

}

}

Найдём одинаковые свойства двух экземпляров класса Person:

var male = new Person { 

Age = 41,

FirstName = "John",

LastName = "Smith",

Male = true

};

var female = new Person {

Age = 41,

FirstName = "Jane",

LastName = "Smith",

Male = false

};

foreach(var prop in male.PublicEqualProps(female))

Console.WriteLine(prop.Name);

Вывод:

Age

LastName



Полный список примеров можно скачать здесь https://code.msdn.microsoft.com/101-LINQ-Samples-3fb9811b



Продолжение следует…



Источник: https://docs.microsoft.com/en-us/dotnet/standard/using-linq