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

ЖАНРЫ

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

// Создать анонимный тип, состоящий из еще одного анонимного типа.

var purchaseItem = new {

TimeBought = DateTime.Now,

ItemBought =

new {Color = "Red", Make = "Saab", CurrentSpeed = 55},

Price = 34.000};

Анонимные типы часто применяются в LINQ, когда необходимо проецировать в новые формы данных на лету. Например, предположим, что есть коллекция объектов

Person
, и вы хотите использовать LINQ для получения информации о возрасте и номере
карточки социального страхования в каждом объекте. Применяя проецироавние LINQ, можно предоставить компилятору возможность генерации нового анонимного типа, который содержит интересующую информацию.

Роль LINQ

На этом краткий обзор средств языка С#, которые позволяют LINQ делать свою работу, завершен. Однако важно понимать, зачем вообще нужен язык LINQ. Любой разработчик программного обеспечения согласится с утверждением, что значительное время при программировании тратится на получение и манипулирование данными. Когда говорят о "данных", на ум немедленно приходит информация, хранящаяся внутри реляционных баз данных. Тем не менее, другими популярными местоположениями для данных являются документы XML или простые текстовые файлы.

Данные могут находиться в многочисленных местах помимо указанных двух распространенных хранилищ информации. Например, пусть имеется массив или обобщенный тип

List<T>
, содержащий 300 целых чисел, и требуется получить подмножество, которое удовлетворяет заданному критерию (например, только четные или нечетные числа, только простые числа, только неповторяющиеся числа больше 50). Или, возможно, при использовании API-интерфейсов рефлексии необходимо получить в массиве элементов Туре только описания метаданных для каждого класса, производного от какого-то родительского класса. На самом деле данные находятся повсюду.

До появления версии .NET 3.5 взаимодействие с отдельной разновидностью данных требовало от программистов применения совершенно несходных API-интерфейсов. В табл. 13.1 описаны некоторые популярные API-интерфейсы, используемые для доступа к разнообразным типам данных (наверняка вы в состоянии привести и другие примеры).

Разумеется, с такими подходами к манипулированию данными не связано ничего плохого. В сущности, вы можете (и будете) работать напрямую с ADO.NET, пространствами имен XML, службами рефлексии и разнообразными типами коллекций. Однако основная проблема заключается в том, что каждый из API-интерфейсов подобного рода является "самостоятельным островком", трудно интегрируемым с другими. Правда, можно (например) сохранить объект

DataSet
из ADO.NET в документ XML и затем манипулировать им посредством пространств имен
System.xml
, но все равно манипуляции данными остаются довольно асимметричными.

В рамках API-интерфейса LINQ была предпринята попытка предложить программистам согласованный, симметричный способ получения и манипулирования "данными" в широком смысле этого понятия. Применяя LINQ, прямо внутри языка программирования C# можно создавать конструкции, которые называются выражениями запросов. Такие выражения запросов основаны на многочисленных операциях запросов, которые намеренно сделаны похожими внешне и по поведению (но не идентичными) на выражения SQL.

Тем не менее, трюк заключается в том, что выражение запроса может использоваться для взаимодействия с разнообразными типами данных — даже с теми, которые не имеют ничего общего с реляционными базами данных. Строго говоря, LINQ представляет собой термин, в целом описывающий сам подход доступа к данным. Однако в зависимости от того, где применяются запросы LINQ, вы встретите разные обозначения вроде перечисленных ниже.

LINQ to Objects. Этот термин

относится к действию по применению запросов LINQ к массивам и коллекциям.

LINQ to XML. Этот термин относится к действию по использованию LINQ для манипулирования и запрашивания документов XML.

LINQ to Entities. Этот аспект LINQ позволяет использовать запросы LINQ внутри API-интерфейса ADO.NET Entity Framework (EF) Core.

Parallel LINQ (PLINQ). Этот аспект делает возможной параллельную обработку данных, возвращаемых из запроса LINQ.

В настоящее время LINQ является неотъемлемой частью библиотек базовых классов .NET Core, управляемых языков и самой среды Visual Studio.

Выражения LINQ строго типизированы

Важно также отметить, что выражение запроса LINQ (в отличие от традиционного оператора SQL) строго типизировано. Следовательно, компилятор C# следит за этим и гарантирует, что выражения оформлены корректно с точки зрения синтаксиса. Инструменты вроде Visual Studio могут применять метаданные для поддержки удобных средств, таких как IntelliSense, автозавершение и т.д.

Основные сборки LINQ

Для работы с LINQ to Objects вы должны обеспечить импортирование пространства имен

System.Linq
в каждом файле кода С#, который содержит запросы LINQ. В противном случае возникнут проблемы. Удостоверьтесь, что в каждом файле кода, где используется LINQ, присутствует следующий оператор
using
:

using System.Linq;

Применение запросов LINQ к элементарным массивам

Чтобы начать исследование LINQ to Objects, давайте построим приложение, которое будет применять запросы LINQ к разнообразным объектам типа массива. Создайте новый проект консольного приложения под названием

LinqOverArray
и определите в классе
Program
статический вспомогательный метод по имени
QueryOverStrings
. Внутри метода создайте массив типа
string
, содержащий несколько произвольных элементов (скажем, названий видеоигр). Удостоверьтесь в том, что хотя бы два элемента содержат числовые значения и несколько элементов включают внутренние пробелы:

static void QueryOverStrings

{

// Предположим, что есть массив строк.

string[] currentVideoGames = {"Morrowind", "Uncharted 2",

"Fallout 3", "Daxter", "System
Shock 2"};

}

Теперь модифицируйте файл

Program.cs
с целью вызова метода
QueryOver Strings
:

Console.WriteLine("***** Fun with LINQ to Objects *****\n");

QueryOverStrings;

Console.ReadLine;

При работе с любым массивом данных часто приходится извлекать из него подмножество элементов на основе определенного критерия. Возможно, требуется получить только элементы, которые содержат число (например, "System Shock 2", "Uncharted 2" и "Fallout 3"), содержат заданное количество символов либо не содержат встроенных пробелов (скажем, "Morrowind" или "Daxter"). В то время как такие задачи определенно можно решать с использованием членов типа

System.Array
, прикладывая приличные усилия, выражения запросов LINQ значительно упрощают процесс.

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