Cómo ordenar una lista…será por opciones!!

El método más habitual para comparar una lista es utilizar el método Sort. Este método utiliza internamente el método CompareTo de los elementos que la lista contiene.

Con datos simples, como un string o un int, no es necesario hacer nada especial para ordenar la lista pero si tenemos una lista de datos más completos, por ejemplo, una lista de entidades, deberemos hacer algo más.

Supongamos que tenemos una entidad que tiene dos propiedades; nombre y fecha, y queremos tener la posibilidad de ordenar por la fecha, tanto de forma ascendente como descendente.

   1: public class MiEntidad
   2: {
   3:     public string Nombre { get; set; }
   4:     public DateTime Fecha { get; set; }
   5: }

Opción 1: La primera opción es que nuestra entidad implemente la interfaz IComparable. Ésto nos obligará a implementar un método adicional en nuestra clase, llamado CompareTo. Éste método será al que se llame cuando se llame al método Sort de la lista.

   1: public class MiEntidad : IComparable<MiEntidad>
   2: {
   3:     public string Nombre { get; set; }
   4:     public DateTime Fecha { get; set; }
   5:     
   6:     public int CompareTo(MiEntidad other)
   7:     {
   8:         return this.Fecha.CompareTo(other.Fecha);
   9:     }
  10: }

 

Pero ¿ qué pasa si queremos ordenar una lista de objetos y no tenemos acceso al código de la misma y no podemos implementar este método adicional?

Opción 2: Tendremos que crear una nueva clase que implemente IComparer. Esta clase incluya la lógica necesaria para saber cómo tiene que comparar dos objetos de tipo MiEntidad y la emplearemos al llamar al método Sort.

   1: public class MiEntidadComparador : IComparer<MiEntidad>
   2:     {
   3:         private SortOrderEnum sortOrder = SortOrderEnum.Ascending;
   4:  
   5:         public MiEntidadComparador(SortOrderEnum sort)
   6:         {
   7:             this.sortOrder = sort;
   8:         }
   9:  
  10:         public int Compare(MiEntidad x, MiEntidad y)
  11:         {
  12:             if (this.sortOrder.Equals(SortOrderEnum.Ascending))
  13:                 return x.Fecha.CompareTo(y.Fecha);
  14:             else
  15:                 return y.Fecha.CompareTo(x.Fecha);
  16:         }        
  17:     }

Una vez que tenemos la clase, la usaremos al invocar al método Sort.

   1: lista.Sort(new MiEntidadComparador(SortOrderEnum.Descending));
   2: foreach (MiEntidad me in lista)
   3:     Console.WriteLine(me.Nombre);

Opción 3: Si aún así no nos apetece hacer esta clase, siempre podemos usar un delegado.

   1: lista.Sort(
   2:         delegate(MiEntidad x, MiEntidad y)
   3:         {
   4:             return x.Fecha.CompareTo(y.Fecha);
   5:         }); 

Opción 4: Pero todavía hay más opciones, esta vez usando LINQ. Eso sí, recuerda que debes LINQ está disponible a partir de la versión 3.5 de Framework.

   1: var listaNombre = from c in lista
   2:         orderby c.FECHA descending
   3:         select c.Nombre;
   4: foreach (string nombre in listaNombre)
   5:     Console.WriteLine(nombre);

Opción 4: o lo mismo usando expresiones lambda.

   1: foreach (MiEntidad me in lista.OrderByDescending(x=>x.Fecha).ToList())
   2:     Console.WriteLine(me.Nombre);

Espero que os sea de utilidad!

Published 16/2/2009 18:00 por Ibon Landa
Comparte este post:
http://geeks.ms/blogs/ilanda/archive/2009/02/16/c-243-mo-ordenar-una-lista-ser-225-por-opciones.aspx

Comentarios

# re: Cómo ordenar una lista…será por opciones!!

Muy bien visto! Si queremos ordenar por fecha sería conveniente ponerlo si!

Gracias!

Tuesday, February 17, 2009 5:58 PM por Ibon Landa

# re: Cómo ordenar una lista…será por opciones!!

Amigo, yo para ordenar una lista, hago click sobre la cabecera de la columna que quiero ordenar. En ese momento me aparece un signo ^ si la ordenación fué correcta :P

Saludos

Tuesday, February 17, 2009 9:25 PM por El Bruno

# re: Cómo ordenar una lista…será por opciones!!

Pues sí, esa se me había pasado :-)

Tuesday, February 17, 2009 10:09 PM por Ibon Landa

# re: Cómo ordenar una lista…será por opciones!!

Hola, si ahora quisiera ordenar por dos atributos a la vez ¿cómo debería hacer?.

Supongamos que tienes que ordenar nombre y si el nombre es igual entonces por fecha.

Muchas gracias

Friday, September 25, 2009 5:40 PM por Hernan

# re: Cómo ordenar una lista…será por opciones!!

Hola,

En las tres primeras opciones el método de comparación recibe dos entidades. En el ejemplo, dentro del método de comparación se compara por la fecha, pero podría incluirse toda la lógica que consideres necesaria, para comparar...por ejemplo, comparar por dos valores de la entidad.

En las dos últimas opciones se pueden especificar dos clausulas de ordenación, de forma parecida a como sería en SQL.

Un saludo,

Saturday, September 26, 2009 11:39 AM por Ibon Landa

# como ordenar una lista de nombre y aellido separado por espacio

Hola tengo una lista muy larga en la que cada fila tiene un nombre y su apellido separado por espacio, y lo que quiero es ordenarla por apellidos. ¿Podríais indicarme como hacerlo?

Tengo W7 y Of10

Friday, August 19, 2011 1:00 PM por templau