Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Design Patterns via C#.pdf
Скачиваний:
154
Добавлен:
17.03.2016
Размер:
13.25 Mб
Скачать

214

Известные применения паттерна в .Net

Важно отметить, что классическое представление паттерна Iterator отличается от представления, рекомендуемого Microsoft. Но суть использования техники «перечисляемый-перечислитель» которая описывается паттерном Iterator при этом не меняется.

Паттерн Iterator, выражен в платформе .NET в виде техники создания составных объектов, основанных на технике «перечисляемый-перечислитель» коллекций, через реализацию интерфейсов IEnumerable и IEnumerator. Оператор автоматической генерации программного кода коллекций - yield, также выражает идею использования паттерна Iterator.

Практически во всех коллекциях, идущих в поставке Microsoft .NET Framework присутствуют реализации итераторов. Следует внимательно подходить к выбору класса коллекции, так как использование неправильного типа коллекции может привести к неоптимальной работе программы. В общем случае не следует использовать типы в пространстве имен System.Collections, если явным образом не используется версия 1.1 платформы .NET Framework. Во всех других случаях рекомендуется использовать универсальные (generic) и параллельные коллекции, так как они оптимизированы, обладают большей типобезопасностью и содержат дополнительные функциональные возможности.

Перед использованием той или иной системной коллекции, необходимо ответить на следующие вопросы:

Вопрос: Требуется ли использовать такой список, элементы которого сразу удаляются после получения их значения?

Ответ: Если да, то имеет смысл рассмотреть возможность использования универсального класса Queue<T>, если требуется работа по принципу (FIFO) или универсального класса Stack<T>, если требуется работа по принципу (LIFO). Для безопасного доступа из нескольких потоков следует использовать параллельные версии очереди или стека - классы ConcurrentQueue<T> или

ConcurrentStack<T> соответственно.

Вопрос: Требуется ли получать доступ к элементам коллекции в определенном порядке (FIFO, LIFO) или в произвольным порядке?

Ответ: Если да, то рекомендуется использовать класс Queue, универсальный класс Queue<T> или универсальный класс ConcurrentQueue<T>, которые предоставляют доступ по принципу FIFO. Класс Stack, универсальный класс Stack<T> или универсальный класс ConcurrentStack<T> предоставляют доступ по принципу LIFO.

Универсальный класс LinkedList<T> предоставляет последовательный доступ от начала списка к концу списка или наоборот.

Вопрос: Необходимо ли получать доступ к элементам коллекции по индексу?

Ответ: Если да, то рекомендуется использовать классы ArrayList и StringCollection, и универсальный класс List<T>, которые предоставляют доступ к своим элементам по индексу, начиная отсчет с нулевого индекса.

Классы Hashtable, SortedList, ListDictionary и StringDictionary, а также универсальные классы Dictionary<TKey, TValue> и SortedDictionary<TKey, TValue> предоставляют доступ к своим элементам по ключу.

Классы NameObjectCollectionBase и NameValueCollection, а также универсальные классы KeyedCollection<TKey, TItem> и SortedList<TKey, TValue> предоставляют доступ к своим элементам по индексу с отсчетом от нуля или по ключу.

Вопрос: Будет ли каждый элемент содержать только одно значение, сочетание из одного ключа и одного значения или сочетание из одного ключа и нескольких значений?

Ответ: Одно значение. Можно использовать любую из коллекций, основанных на интерфейсе IList или на универсальном интерфейсе IList<T>.

215

Один ключ и одно значение. Можно использовать любую из коллекций, основанных на интерфейсе

IDictionary или на универсальном интерфейсе IDictionary<TKey, TValue>.

Одно значение с внедренным ключом. Можно использовать универсальный класс

KeyedCollection<TKey, TItem>.

Один ключ и несколько значений. Можно использовать класс NameValueCollection.

Вопрос: Требуется ли сортировка элементов в порядке, отличном от того порядка в котором элементы поступают (добавляются) в коллекцию?

Ответ: Если да, то рекомендуется использовать класс Hashtable, который сортирует свои элементы по их хэш-коду.

Класс SortedList и универсальные классы SortedDictionary<TKey, TValue> и SortedList<TKey, TValue> сортируют свои элементы по их ключам на основе реализации интерфейса IComparer и универсального интерфейса IComparer<T>.

Класс ArrayList предоставляет метод Sort, который принимает реализацию IComparer в качестве параметра. Его универсальный аналог — универсальный класс List<T> предоставляет метод Sort, который принимает реализацию универсального интерфейса IComparer<T> в качестве параметра.

Вопрос: Необходимо ли организовать быстрый поиск по коллекции, а также быстрое помещение новых элементов в коллекцию и быстрое извлечение существующих элементов из коллекции?

Ответ: Если да, то рекомендуется использовать класс ListDictionary, так как он работает быстрее, чем Hashtable для небольших коллекций (10 элементов или меньше). Универсальный класс Dictionary<TKey, TValue> предоставляет более быстрый просмотр, чем универсальный класс SortedDictionary<TKey, TValue>. Многопоточной реализацией является класс

ConcurrentDictionary<TKey, TValue>. Класс ConcurrentBag<T> предоставляет быструю многопоточную вставку для неупорядоченных данных.

Вопрос: Требуется ли использовать коллекцию только для хранения строк?

Ответ: Если да, то рекомендуется использовать классы StringCollection (основанный на IList) и StringDictionary (основанный на IDictionary) которые находятся в пространстве имен

System.Collections.Specialized.

Кроме того, можно использовать любой из универсальных классов коллекций из пространства имен System.Collections.Generic как строго типизированную строковую коллекцию, указав класс String в качестве параметра типа.

Соседние файлы в предмете [НЕСОРТИРОВАННОЕ]