jueves, 28 de agosto de 2008

Colecciones en .NET, IEnumerator, IEnumerable.

 

Las colecciones son uno de los recursos más utilizados (sino el más) dentro del mundo de .net, es importante comprender bien su funcionamiento y su potencial, ya que una decisión correcta nos puede facilitar mucho el trabajo y hasta tener impácto en el rendimiento de nuestra aplicación.

En .net 2.0 existen tres tipos de colecciones:

  • Colecciones normales
  • Colecciones especializadas
  • Coleccioner genéricas

Vamos a comenzar por el principio, por las colecciones normales, y para ser más básico aún vamos a ver la interface que todos usan.

Con ustedes IEnumerator

 Esta interface está hasta en la sopa, todas las colecciones de .net la utilizan y es importante comprender cómo funciona, el bucle foreach (uno de los más grandes inventos de la época) también y la interface IEnumerable la base de Linq, entonces vamos a analizarla

public interface IEnumerator
{
    object Current { get; }
    bool MoveNext();
    void Reset();
}

La idea es que la clase que implemente IEnumerator posee una conjunto de elemento de un tipo (una lista, un array, un vector) y los métodos de IEnumerator me permite acceder a esta lista de una manera estándar.

  • Current: esta propiedad devuelve el elemento actual donde se encuentra apuntada la lista, es decir, sila lista tiene 10 elemento por convensión el método Current nos devuelve el primer elemento.
  •  MoveNext: Con este método le decimos a la clase que lo implementa que mueva su posición al siguiente elemento en su lista, es decir, si actualmente está en el elemento 5 luego de ejecutar MoveNext deberá pasar al 6 y devolverá true, siempre y cuando el 6 exista, en caso de no existir el elemento 6 no se moverá y devolverá false, en lugar de true. Con este método podemos poner un bucle while por ejemplo y movernos por toda la lista.
  •  Reset: pone al principio la posición actual de la lista.

Se va la segunda IEnumerable

IEnumerator no sirve de mucho sin su fiel aliado, IEnumerable, esta interface es muy sencilla y no hace más que devolver en su único método la interface IEnumerator, veamos su firma

public interface IEnumerable 
{ 
    IEnumerator GetEnumerator(); 
}

 Exáctamente esto es lo que tenemos que implementar si queremos que una clase nuestra se pueda iterar con un bucle foreach, vamos a ver un pequeño ejemplo.

[TestFixture]
public class Class1
{
    [Test]
    public void ProbarLista()
    {
        ContenedorLista lista = new ContenedorLista(new object[]{1,2,3,4,5,6,7,8,9,0});

        foreach (int nro in lista)
        {
            NUnit.Core.TestContext.Out.WriteLine(nro);
        }

        Console.ReadLine();
    }
}
public class ContenedorLista: IEnumerable
{
    IEnumerator _istaPropia;

    public ContenedorLista(object[] lista)
    {
        _istaPropia = new ListaPropia(lista);
    }

    public IEnumerator GetEnumerator()
    {
        return _istaPropia;
    }
}

public class ListaPropia : IEnumerator
{
    object[] _lista;
    int _posicion;

    public ListaPropia(object[] lista)
    {
        _lista = lista;
        this.Reset();
    }

    public object Current 
    {
        get 
        {
            return _lista[_posicion];
        }
    }

    public bool MoveNext()
    {
        if (++_posicion < _lista.Length)
        {
            return true;
        }
        else
        {
            return false;
        }
    }

    public void Reset()
    {
        _posicion = -1;
    }
}

Mágico sin duda, bueno por ahora esta primer entrega sobre colecciones termina, la próxima vamos a ver otras interfaces, saludos.

12 comentarios:

Pablo dijo...

Hola amigo, he llegado a tu blog a traves de planeta codigo, y te quiero hacer una observación sobre los colores del diseño del blog....fondo negro con letras grises dificulta muchisimo la lectura sobre todo si uno tiene una definición muy alta en el monitor....no soy experto en diseño, pero creo que con letras de color blanco puede mejorar la cosa.
Por lo demas, muy interesantes los temas sobre listas que has estado tocando en tus posts.
Salu2

Leonardo Micheloni dijo...

Gracias por la observación, como verás tampoco soy un experto en diseño, de echo el diseño no es mio si miras al pie del mismo lo verás, de todos modos coincido contigo, ya lo he cambiado, saludos y suerte.

MAC dijo...

Hola, a mi también me gustaría acotar, que el alto contraste con tu pantalla y el resto de la sala donde estés seguramente te produzca deslumbramiento, y es muy malo para la vista. por eso ya no se usa mas las aplicaciones con colores a lo matrix.
Un saludo

Leonardo Micheloni dijo...

Gracias por el comentario, de todos modos voy cambiando de fondos para...variar :)

saludos

Quijote dijo...

Jajajaja... me causó gracia el que reparen de los colores del blog, creo que eso amerita un mensaje privado o algo así ;-)

En fin, está bueno el resumen introductorio a las interfaces. Gracias por tu tiempo Leonardo!. Un saludo.

Leonardo Micheloni dijo...

Gracsi por tu comentario Quijote, son gajes del oficio :)

jpriet dijo...

mas importante que los colores, creo que sería que repasaras la redación de lo que pegas desde el traductor de google. ;-)

jpriet dijo...
Este comentario ha sido eliminado por el autor.
Leonardo Micheloni dijo...

Gracias por el comentario jpriet, por desgracia para mí el texto es de mi autoría así que es un problema más gravé aún :P

jpriet dijo...

pues retiro lo dicho sobre google.
Creo que todavía funciona una aplicación mia que hice hace años y que hablaba de "tareas resuletas" :-)

IcebergDelphi dijo...
Este comentario ha sido eliminado por el autor.
IcebergDelphi dijo...

Hola muy buena informacion, aun soy algo nuevo con C# , me gustaria saber en que casos se utilizan esas colecciones o que estan suplantando? es decir envez de usar un foreach es mejor usar el IEnumerable, etc? No muy entiendo esa parte, Gracias