¿Cuál es la diferencia entre IEnumerable y Array, IList y List?

¿Cuál es la diferencia entre IEnumerable y Array ?

¿Cuál es la diferencia entre IList y List ?

Estos parecen tener la misma función.

IEnumerable proporciona solo una funcionalidad mínima “iterable”. Puedes recorrer la secuencia, pero eso es todo. Esto tiene desventajas, por ejemplo, es muy ineficiente contar elementos usando IEnumerable, o para obtener el enésimo elemento, pero también tiene ventajas, por ejemplo, un IEnumerable podría ser una secuencia sin fin, como la secuencia de números primos.

Array es una colección de tamaño fijo con acceso aleatorio (es decir, puede indexar en ella).

List es una colección de tamaño variable (es decir, puede agregar y eliminar elementos) con acceso aleatorio.

IList es una interfaz que abstrae la funcionalidad de la lista (contar, agregar, eliminar, acceder al indexador) lejos de las diversas clases concretas, como List, BindingList, ObservableCollection, etc.

IEnumerable es una interfaz que permite la iteración a través de una colección de elementos (por ejemplo, a través de la palabra clave foreach).

Una matriz es .NET intrínseca. Tiene elementos del mismo tipo, pero tiene un tamaño fijo. Una vez que crea una matriz con x elementos, no puede crecer ni reducirse.

IList define la interfaz para una lista y también implementa IEnumerable.

List implementa la interfaz IList; es un tipo concreto de lista.

La diferencia entre las listas .NET y las matrices es que las listas pueden tener elementos agregados: crecen lo suficiente como para contener todos los elementos necesarios. La lista almacena esto internamente en una matriz y, cuando la matriz ya no es lo suficientemente grande como para contener todos los elementos, se crea una nueva matriz y se copian los elementos.

IList y arrays implementan IEnumerable. Así es como funcionan las interfaces: las clases implementan el contrato y se comportan de manera similar y pueden ser tratadas de manera similar como resultado (usted sabe que la clase implementa IEnumerable, no necesita saber cómo o por qué). Te sugiero que leas las interfaces y demás.

IEnumerable e IList son interfaces . Array y List son clases. Array implementa IEnumerable. List implementa IList que extiende IEnumerable.

Editar: como mencionó itowlson en un comentario, Array también implementa IList.

La generación de una colección IEnumerable es floja. Ejemplo:

 public IEnumerable GetTwoInts() { yield return 1; yield return 2; } public void Something() { var twoInts = GetTwoInts(); } 

En el método Algo, la llamada a GetTwoInts () no dará como resultado el método GetTwoInts que se está ejecutando, ya que la enumeración nunca se repite.

IEnumerable es una interfaz de propósito general que muchas clases usan, como Array , List y String , para permitir que alguien itere sobre una colección. Básicamente, es lo que impulsa la statement foreach .

IList es generalmente la forma en que expone las variables de tipo List a los usuarios finales. Esta interfaz permite el acceso aleatorio a la colección subyacente.

Esta es una publicación anterior, pero aún así pensé en responder. IEnumerable es un comportamiento mientras Array es una estructura de datos (colección contigua de elementos con tamaño fijo, lo que facilita el acceso a los elementos por índices). Cuando una Matriz implementa IEnumerable, se supone que también representa la propiedad inherente de IEnumerable (de facilitar la iteración sobre la colección).

Para complementar las otras respuestas, tenga en cuenta que hay una diferencia de rendimiento entre IList y List al ejecutar una instrucción foreach.

Esto se debe a que el objeto iterador devuelto por List.GetEnumerator es un tipo de valor, mientras que el devuelto por IList.GetEnumerator es un tipo de referencia, y por lo tanto requiere una asignación de memoria (consulte Enumerador del tipo de valor de la lista en c # ).

En mi opinión, IList no es una interfaz muy buena de todos modos. Por ejemplo, llamar a Add puede lanzar (ver ¿Por qué array implementa IList? ). Si necesita encapsulación, sería mejor usar IEnumerable o IReadOnlyList .