Чтение онлайн

ЖАНРЫ

Язык программирования C#9 и платформа .NET5
Шрифт:

Исследование операций запросов LINQ

В языке C# предопределено порядочное число операций запросов. Некоторые часто применяемые из них перечислены в табл. 13.2. В дополнение к неполному списку операций, приведенному в табл. 13.3, класс

System.Linq.Enumerable
предлагает набор методов, которые не имеют прямого сокращенного обозначения в виде операций запросов С#, а доступны как расширяющие методы. Эти обобщенные методы можно вызывать для трансформации результирующего набора разными способами (
Reverse<>
,
ToArray<>
,
ToList<>
и т.д.). Некоторые из них применяются для извлечения одиночных элементов из результирующего
набора, другие выполняют разнообразные операции над множествами (
Distinct<>
,
Union<>
,
Intersect<>
и т.п.), а есть еще те, что агрегируют результаты (
Count<>
,
Sum<>
,
Min<>
,
Мах<>
и т.д.).

Чтобы приступить к исследованию более замысловатых запросов LINQ, создайте новый проект консольного приложения по имени

FunWithLinqExpressions
и затем определите массив или коллекцию некоторых выборочных данных. В проекте
FunWithLinqExpressions
вы будете создавать массив объектов типа
ProductInfo
, определенного следующим образом:

namespace FunWithLinqExpressions

{

class ProductInfo

{

public string Name {get; set;} = "";

public string Description {get; set;} = "";

public int NumberInStock {get; set;} = 0;

public override string ToString

=> $"Name={Name}, Description={Description},

Number in Stock={NumberInStock}";

}

}

Теперь заполните массив объектами

ProductInfo
в вызывающем коде:

Console.WriteLine("***** Fun with Query Expressions *****\n");

// Этот массив будет основой для тестирования...

ProductInfo[] itemsInStock = new[] {

new ProductInfo{ Name = "Mac's Coffee",

Description = "Coffee with TEETH", NumberInStock = 24},

new ProductInfo{ Name = "Milk Maid Milk",

Description = "Milk cow's love", NumberInStock = 100},

new ProductInfo{ Name = "Pure Silk Tofu",

Description = "Bland as Possible", NumberInStock = 120},

new ProductInfo{ Name = "Crunchy Pops",

Description = "Cheezy, peppery goodness",
NumberInStock = 2},

new ProductInfo{ Name = "RipOff Water",

Description = "From the tap to your wallet",
NumberInStock = 100},

new ProductInfo{ Name = "Classic Valpo Pizza",

Description = "Everyone loves
pizza!", NumberInStock = 73}

};

// Здесь мы будем вызывать разнообразные методы!

Console.ReadLine;

Базовый

синтаксис выборки

Поскольку синтаксическая корректность выражения запроса LINQ проверяется на этапе компиляции, вы должны помнить, что порядок следования операций критически важен. В простейшем виде каждый запрос LINQ строится с использованием операций

from
,
in
и
select
. Вот базовый шаблон, который нужно соблюдать:

var результат =

from сопоставляемыйЭлемент in контейнер

select сопоставляемыйЭлемент;

Элемент после операции

from
представляет элемент, соответствующий критерию запроса LINQ; именовать его можно по своему усмотрению. Элемент после операции in представляет контейнер данных, в котором производится поиск (массив, коллекция, документ XML и т.д.).

Рассмотрим простой запрос, не делающий ничего кроме извлечения каждого элемента контейнера (по поведению похожий на SQL-оператор

SELECT *
в базе данных):

static void SelectEverything(ProductInfo[] products)

{

// Получить все!

Console.WriteLine("All product details:");

var allProducts = from p in products select p;

foreach (var prod in allProducts)

{

Console.WriteLine(prod.ToString);

}

}

По правде говоря, это выражение запроса не особенно полезно, т.к. оно выдает подмножество, идентичное содержимому входного параметра. При желании можно извлечь только значения

Name
каждого товара, применив следующий синтаксис выборки:

static void ListProductNames(ProductInfo[] products)

{

// Теперь получить только наименования товаров.

Console.WriteLine("Only product names:");

var names = from p in products select p.Name;

foreach (var n in names)

{

Console.WriteLine("Name: {0}", n);

}

}

Получение подмножества данных

Чтобы получить определенное подмножество из контейнера, можно использовать операцию

where
. Общий шаблон запроса становится таким:

var результат =

from элемент in контейнер

where булевскоеВыражение

select элемент;

Обратите внимание, что операция where ожидает выражение, результатом вычисления которого является булевское значение. Например, чтобы извлечь из аргумента

ProductInfo[]
только товарные позиции, складские запасы которых составляют более 25 единиц, можно написать следующий код:

Поделиться с друзьями: