Колекції у

Майже кожен день ми використовуємо ті чи інші колекції. Найчастіше навіть не замислюючись, які і чому використовуємо. У статті розглянемо ключові механізми роботи з колекціями у .NET. Як старт розглянемо ієрархію деяких інтерфейсів у .NET.

даних

Більшість колекцій реалізує інтерфейс IEnumerable явно чи неявно. Так як тип Array не є Generic типом, то він успадковує лише IEnumerable, а не IEnumerable.

IEnumerable

Інтерфейс IEnumerable показує, що тип реалізує GetEnumerator . Стає доступна конструкція foreach. З IEnumerable часто використовуються розширення з System.Linq. Generic інтерфейс використовується при поверненні із запитів (наприклад до бази даних або інших колекцій). Запит, який вибирає цілі числа буде типу IEnumerable .

IEnumerable підходить для перебору за колекцією. Ви не можете змінити (додати або видалити) дані з IEnumerable. У разі запиту до бази даних на сервері, запит поверне всі дані (без фільтрації).

IEnumerable

IEnumerable

IQueryable

Щоразу, коли ми стикаємося з великою кількістю даних, необхідно подумати, яку колекцію або який тип використовувати для роботи з ними. На відміну від IEnumerable – IQueryable пропонує високу продуктивність у разі роботи з великим обсягом даних. IQueryable попередньо фільтрує дані на запит, а потім надсилає тільки відфільтровані дані клієнту.

Різниця між IQueryable та IEnumerable

Основна відмінність між цими інтерфейсами в тому, що IEnumerable працює з усім масивом даних, а IQueryable з відфільтрованим. IEnumerable отримує всі дані на стороні сервера і завантажує їх в пам'ять, а потім дозволяє зробити фільтрацію за даними зпам'яті. Коли робиться запит до бази даних, IQueryable виконує запит на серверній стороні та у запиті застосовує фільтрацію.

Коли що застосовувати

IEnumerable

  1. IEnumerable може рухатися тільки вперед по колекції, він не може йти назад
  2. Добре підходить для роботи з даними в пам'яті (списки, масиви)
  3. Підходить для LINQ to Object та LINQ to XML
  4. Підтримує відкладене виконання
  5. Не підтримує довільних запитів
  6. Не підтримує ліниве завантаження
  7. Методи розширення, що працюють з IEnumerable приймають функціональні об'єкти

IQueryable

  1. IQueryable може рухатися тільки вперед по колекції, він не може йти назад
  2. IQueryable краще працює з запитами до бази даних (поза пам'яттю)
  3. Підходить для LINQ to SQL
  4. Підтримує відкладене виконання
  5. Підтримує довільні запити (використовуючи CreateQuery та метод Execute)
  6. Підтримує ліниве завантаження
  7. Методи розширення, що працюють з IQueryable приймають об'єкти вираження (expression tree)

ICollection

Аналогічно з IEnumerable існує дві версії цього інтерфейсу. ICollection та ICollection .

ICollection успадковується від IEnumerable. Це означає, що додатково необхідно реалізувати інтерфейс IEnumerable. Інтерфейс визначає розмір, перерахування та методи синхронізації для всіх не generic колекцій.

ICollection

На відміну від IEnumerable та IEnumerable - ICollection відрізняється від свого не generic еквівалента.

Як і все, що ми розглянули раніше IList існує у звичайній та generic версії. Розглянемо не єдину версію інтерфейсу IList.

На додаток до інтерфейсу ICollection та IEnumerable , IListнадає методи для додавання та видалення елементів з колекції. Він також дозволяє дізнатися індекс елемента всередині колекції. Також IList реалізує індексатор, щоб отримати доступ до об'єктів через квадратні дужки. Наприклад так:

Generic версія відрізняється від свого побратима. А саме:

Згадавши ICollection , де оголошені методи для роботи з колекцією IList доповнює лише методами, що бракують: пошук по елементу і індексатор.

Висновок

Тепер, розглянувши всі інтерфейси, ми можемо вирішити, який саме слід застосовувати в конкретній ситуації. Як правильно, це гарна ідея залежати лише від тих речей, які реально потрібні.

Використовуючи IEnumerable замість IList, ми захищаємося від незапланованих змін у колекції. Використовуючи IEnumerable, ваш метод може використовувати будь-який тип, що реалізує IEnumerable (з малюнка на початку статті це будь-яка колекція). Код програми може легко змінитися в майбутньому нічого не зламавши, замінивши IEnumerable на сильніший інтерфейс.

  • IEnumerable — єдине, що потрібно пройти по всіх елементах колекції. Read-only доступ до колекції
  • ICollection — можливість змінювати колекцію та дізнатися про її розмір
  • IList - можливість зміни колекції. У доповненні стає доступним порядок (індекс елементів)
  • List — відповідно до одного з принципів SOLID (Dependency inversion) — завжди слід залежати від абстракцій, ніж їх реалізацій.

За рамками цієї статті опинилися інші цікаві колекції .NET, наприклад черга (Queue), стек (Stack), хеш таблиця (HashTable) та словник (Dictionary).