Рейтинговые книги
Читем онлайн C# 4.0: полное руководство - Герберт Шилдт

Шрифт:

-
+

Интервал:

-
+

Закладка:

Сделать
1 ... 178 179 180 181 182 183 184 185 186 ... 294

Оператор запроса  Эквивалентный метод запроса

select            Select(selector)

where             Where(predicate)

orderby           OrderBy(keySelector) или

                  OrderByDescending(keySelector)

join              Join(inner, outerKeySelector,

                    innerKeySelector, resultSelector)

group             GroupBy(keySelector)

За исключением метода Join(), остальные методы запроса принимают единственный аргумент, который представляет собой объект некоторой разновидности обобщенного типа Func<T, TResult>. Это тип встроенного делегата, объявляемый следующим образом:

delegate TResult Func<in Т, out TResult>(Т arg)

где TResult обозначает тип результата, который дает делегат, а Т — тип элемента. В методах запроса аргументы selector, predicate или keySelector определяют действие, которое предпринимает метод запроса. Например, в методе Where() аргумент predicate определяет порядок отбора данных в запросе. Каждый метод запроса возвращает перечислимый объект. Поэтому результат выполнения одного метода запроса можно использовать для вызова другого, соединяя эти методы в цепочку.

Метод Join() принимает четыре аргумента. Первый аргумент (inner) представляет собой ссылку на вторую объединяемую последовательность, а первой является последовательность, для которой вызывается метод Join(). Селектор ключа для первой последовательности передается в качестве аргумента outerKeySelector, а селектор ключа для второй последовательности — в качестве аргумента innerKeySelector. Результат объединения обозначается как аргумент resultSelector. Аргумент outerKeySelector имеет тип Func<T0uter, ТКеу>, аргумент innerKeySelector — тип Func<TInner, ТКеу>, тогда как аргумент resultSelector — тип Func<T0uter, Tinner, TResult>, где TOuter — тип элемента из вызывающей последовательности; Tinner — тип элемента из передаваемой последовательности; TResult — тип элемента из объединяемой в итоге последовательности, возвращаемой в виде перечислимого объекта.

Аргумент метода запроса представляет собой метод, совместимый с указываемой формой делегата Funс, но он не обязательно должен быть явно объявляемым методом. На самом деле вместо него чаще всего используется лямбда-выражение. Как пояснялось в главе 15, лямбда-выражение обеспечивает более простой, но эффективный способ определения того, что, по существу, является анонимным методом, а компилятор C# автоматически преобразует лямбда-выражение в форму, которая может быть передана в качестве параметра делегату Funс. Благодаря тому что лямбда-выражения обеспечивают более простой и рациональный способ программирования, они используются во всех примерах, представленных далее в этом разделе.

Формирование запросов с помощью методов запроса

Используя методы запроса одновременно с лямбда-выражениями, можно формировать запросы, вообще не пользуясь синтаксисом, предусмотренным в C# для запросов. Вместо этого достаточно вызвать соответствующие методы запроса. Обратимся сначала к простому примеру. Он представляет собой вариант первого примера программы из этой главы, переделанный с целью продемонстрировать применение методов запроса Where() и Select() вместо соответствующих операторов.

// Использовать методы запроса для формирования простого запроса.

// Это переделанный вариант первого примера программы из настоящей главы.

using System;

using System.Linq;

class SimpQuery {

  static void Main() {

    int[] nums = { 1, -2, 3, 0, -4, 5 };

    // Использовать методы Where() и Select() для

    // формирования простого запроса.

    var posNums = nums.Where(n => n > 0).Select(r => r);

    Console.Write("Положительные значения из массива nums: ");

    // Выполнить запрос и вывести его результаты,

    foreach(int i in posNums) Console.Write(i + " ") ;

    Console.WriteLine();

  }

}

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

Положительные значения из массива nums: 1 3 5

Обратите особое внимание в данной программе на следующую строку кода.

var posNums = nums.Where(n => n > 0).Select(r => r);

В этой строке кода формируется запрос, сохраняемый в переменной posNums. По этому запросу, в свою очередь, формируется последовательность положительных значений, извлекаемых из массива nums. Для этой цели служит метод Where(), отбирающий запрашиваемые значения, а также метод Select(), избирательно формирующий из этих значений окончательный результат. Метод Where() может быть вызван для массива nums, поскольку во всех массивах реализуется интерфейс IEnumerable<T>, поддерживающий методы расширения запроса.

Формально метод Select() в рассматриваемом здесь примере не нужен, поскольку это простой запрос. Ведь последовательность, возвращаемая методом Where(), уже содержит конечный результат. Но окончательный выбор можно сделать и по более сложному критерию, как это было показано ранее на примерах использования синтаксиса запросов. Так, по приведенному ниже запросу из массива nums возвращаются положительные значения, увеличенные на порядок величины.

var posNums = nums.Where(n => n > 0) .Select (r => r * 10);

Как и следовало ожидать, в цепочку можно объединять и другие операции над данными, получаемыми по запросу. Например, по следующему запросу выбираются положительные значения, которые затем сортируются по убывающей и возвращаются в виде результирующей последовательности:

var posNums = nums.Where(n => n > 0).OrderByDescending(j => j);

где выражение j => j обозначает, что упорядочение зависит от входного параметра, который является элементом данных из последовательности, получаемой из метода Where().

В приведенном ниже примере демонстрируется применение метода запроса GroupBy(). Это измененный вариант представленного ранее примера.

// Продемонстрировать применение метода запроса GroupBy().

// Это переработанный вариант примера, представленного ранее

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

using System;

using System.Linq;

class GroupByDemo {

  static void Main() {

    string[] websites = {

      "hsNameA.com", "hsNameB.net", "hsNameC.net",

      "hsNameD.com", "hsNameE.org", "hsNameF.org",

      "hsNameG.tv", "hsNameH.net", "hsNamel.tv"

    };

    // Использовать методы запроса для группирования

    // веб-сайтов по имени домена самого верхнего уровня.

    var webAddrs = websites.Where(w => w.LastIndexOf('.') != 1).

          GroupBy(x => x.Substring(x.LastIndexOf(".", x.Length)));

    // Выполнить запрос и вывести его результаты, foreach(var sites in webAddrs) {

    foreach (var sites in webAddrs) {

      Console.WriteLine("Веб-сайты, сгруппированные " +

           "по имени домена " + sites.Key);

      foreach (var site in sites)

        Console.WriteLine(" " + site);

      Console.WriteLine();

    }

  }

}

Эта версия программы дает такой же результат, как и предыдущая. Единственное отличие между ними заключается в том, как формируется запрос. В данной версии для этой цели используются методы запроса.

Рассмотрим другой пример. Но сначала приведем еще раз запрос из представленного ранее примера применения оператора join.

var inStockList = from item in items

  join entry in statusList

    on item.ItemNumber equals entry.ItemNumber

1 ... 178 179 180 181 182 183 184 185 186 ... 294
На этой странице вы можете бесплатно читать книгу C# 4.0: полное руководство - Герберт Шилдт бесплатно.
Похожие на C# 4.0: полное руководство - Герберт Шилдт книги

Оставить комментарий