Отложенное выполнение и отложенное вычисление (LINQ to XML)
Операции по обработке запросов и осей часто реализуются с использованием отложенного выполнения. В этой статье описываются требования и преимущества отложенного выполнения, а также некоторые рекомендации по реализации.
Отложенное выполнение
Отложенное выполнение означает, что вычисление выражения откладывается до тех пор, пока не возникнет действительная потребность в его реализованном значении. Отложенное выполнение может значительно повышать производительность в ситуациях, когда приходится манипулировать большими коллекциями данных, особенно в программах, содержащих ряд последовательных запросов или манипуляций. В лучшем случае отложенное выполнение обеспечивает только один проход по исходной коллекции.
Технологии LINQ предусматривают широкое использование отложенного выполнения как в членах основных классов System.Linq, так и в методах расширений в различных пространствах имен LINQ, таких как System.Xml.Linq.Extensions.
Отложенное выполнение поддерживается непосредственно на языке C# с помощью ключевое слово (справочник по C#) (в виде инструкцииyield-return
) при использовании в блоке итератора. Такой итератор должен возвращать коллекцию типа IEnumerator либо IEnumerator<T> (или одного из производных типов).
Охотное и ленивое вычисление
При создании метода, реализующего отложенное выполнение, необходимо также решать вопрос о том, следует ли реализовывать этот метод с помощью отложенного или безотложного вычисления.
- В случае отложенного вычисления один элемент исходной коллекции обрабатывается при каждом обращении к итератору. Это типичный способ реализации итераторов.
- В случае безотложного вычисления при первом же обращении к итератору обрабатывается вся коллекция. Может также потребоваться временная копия исходной коллекции. Так, метод OrderBy должен отсортировать всю коллекцию, перед тем как возвратить ее первый элемент.
Метод неспешного вычисления обычно обеспечивает более высокую производительность, поскольку он равномерно распределяет затраты на обработку по всему периоду вычисления и сводит к минимуму использование временных данных. Разумеется, при выполнении некоторых операций не остается ничего иного, как материализовать промежуточные результаты.
Пример отложенного выполнения см . в примере отложенного выполнения в C# и Visual Basic.