что такое IEnumerable в .net?
Что такое IEnumerable в .net
Ответ 1
Это... что-то... что вы можете перебрать. Это может быть List или Array или (почти) все, что поддерживает цикл foreach
. Это для того, когда вы хотите использовать объект с циклом foreach
, но не знаете точно, с каким типом вы имеете дело, будь то массив, список или что-то обычное.
Итак, первое преимущество: если ваши методы принимают IEnumerable, а не массив или список, они становятся более мощными, потому что вы можете передавать им более разные типы объектов.
Теперь то, что делает IEnumerable действительно выделяющимся, это итераторные блоки (ключевое слово yield
в С#). Блоки Iterator реализуют интерфейс IEnumerable, такой как List или Array, но они очень особенные, потому что, в отличие от List или Array, они часто удерживают только состояние для одного элемента за раз. Поэтому, если вы хотите, чтобы вы перебирали строки в очень большом файле, вы можете написать блок итератора для обработки ввода файла. Тогда у вас никогда не будет больше одной строки файла в памяти за раз, и если вы закончите цикл раньше (возможно, это был поиск, и вы нашли то, что вам было нужно), вам может не понадобиться читать весь файл. Или, если вы читаете результаты из большого SQL-запроса, вы можете ограничить использование вашей памяти одной записью.
Другая особенность заключается в том, что эта оценка ленива, поэтому, если вы выполняете сложную работу для оценки перечислимого по мере чтения из нее, эта работа не выполняется, пока она не попросит. Это очень полезно, потому что часто (скажем, для поиска снова) вы обнаружите, что вам может вообще не понадобиться выполнять эту работу.
Вы можете думать о IEnumerable, как о том, что это был список вовремя.
Ответ 2
Это интерфейс, реализованный типами Collection в .NET, которые обеспечивают шаблон итератора. Также существует общая версия IEnumerable<T>
.
Синтаксис (который вы редко видите, потому что есть более красивые способы сделать это) для перемещения по коллекции, которая реализует IEnumerable:
IEnumerator enumerator = collection.GetEnumerator();
while(enumerator.MoveNext())
{
object obj = enumerator.Current;
// work with the object
}
Что функционально эквивалентно:
foreach(object obj in collection)
{
// work with the object
}
Если коллекция поддерживает индексы, вы также можете перебирать ее с помощью метода classic for loop, но шаблон Iterator предоставляет некоторые приятные дополнения, такие как возможность добавления синхронизации для потоковой передачи.
Ответ 3
Сначала это интерфейс. Определение в соответствии с MSDN -
Выдает счетчик, который поддерживает простая итерация по неэквивалентным коллекция.
Сказано очень простым способом, что любой объект, реализующий этот интерфейс, обеспечит способ получения перечислителя. Перечислитель используется с foreach
как один пример.
A List реализует интерфейс IEnumerable.
// This is a collection that eventually we will use an Enumertor to loop through
// rather than a typical index number if we used a for loop.
List<string> dinosaurs = new List<string>();
dinosaurs.Add("Tyrannosaurus");
dinosaurs.Add("Amargasaurus");
dinosaurs.Add("Mamenchisaurus");
dinosaurs.Add("Deinonychus");
dinosaurs.Add("Compsognathus");
Console.WriteLine();
// HERE is where the Enumerator is gotten from the List<string> object
foreach(string dinosaur in dinosaurs)
{
Console.WriteLine(dinosaur);
}
// You could do a
for(int i = 0; i < dinosaurs.Count; i++)
{
string dinosaur = dinosaurs[i];
Console.WriteLine(dinosaur);
}
Предпросмотр выглядит более чистым.
Ответ 4
Короткий ответ: все, что вы можете использовать foreach
on.
Ответ 5
using System.Collections;
using static System.Console;
namespace SimpleIterators
{
class X
{
static int i = 0;
public int I
{
get { return i; }
}
public X()
{
WriteLine("X "+i++);
}
}
class Program
{
public static IEnumerable ValueI(X[] tabl)
{
for (int i = 0; i < 10; i++)
yield return tabl[i].I;
}
public static IEnumerable ListClass(X[] tabl)
{
for (int i = 0; i < 10; i++)
yield return tabl[i] = new X();
}
static void Main(string[] args)
{
X[] tabl = new X[10];
foreach (X x in ListClass(tabl));
foreach (int i in ValueI(tabl))
WriteLine("X " + i);
WriteLine("X " + tabl[0].I);
ReadKey();
}
}
}