lunes, 19 de mayo de 2014

Receta No. 2-17 en C#: Selección de Elementos de un Arreglo o Colección

Tabla de Contenido

0. Introducción
1. Problema
2. Solución
3. Discusión de la Solución
3.1 La clausula from
3.2 La clausula where
3.3 La clausula select
4. Práctica: Código Fuente C#
5. Conclusiones
6. Glosario
7. Literatura & Enlaces

0. Introducción

Es el momento de preparar una receta en C# que nos permita seleccionar los elementos de un arreglo utilizando un lenguaje propio de la plataforma .NET: LINQ. Veremos que con este lenguaje de consulta es posible hacer recuperación de elementos de dato de estructuras de datos de manera muy natural (pues se parece al lenguaje de consulta SQL). Al final, en la sección práctica, veremos un ejemplo extendido con el uso de LINQ sobre colecciones genéricas. ¡Empecemos!

1. Problema

El equipo de programadores de Ad Infinitum Systems ha comprobado que uno de los defectos comunes en las aplicaciones creados con el Framework .NET (específicamente, versiones inferiores a 3.5) consiste en la carencia de un lenguaje común para la consulta de datos sobre los elementos de un arreglo o una colección. El desempeño de las aplicaciones también se ve afectado por la práctica artesanal para la composición de algoritmos de selección (búsqueda).

2. Solución

Buscamos, y hallamos que a partir de la versión 3.5 del Framework .NET, los programadores disponemos de un lenguaje de selección (consulta) que nos permite encontrar los elementos de una colección o arreglo de una manera muy práctica y simple: LINQ. Esta va a ser nuestra solución para mejorar los algoritmos de selección y búsqueda de elementos de datos sobre las estructuras de datos mencionadas.

3. Discusión de la Solución

Según [2], LINQ (Language-Integrated Query) es un conjunto de características que extienden las capacidades de consulta para los lenguajes de programación Visual Basic y C#. Entre las capacidades innovadoras de consulta, LINQ, incluye patrones de consulta comprobados, ademas, nos permite realizar actualización sobre los datos. Esto lo hace un lenguaje increíblemente poderoso que lo podemos utilizar, inclusive, para consultas a otras fuentes de datos: bases de datos, documentos XML, conjuntos de datos de ADO.NET, y desde luego, para las colecciones que nos interesan: arreglos y colecciones.

En el caso que nos corresponde, LINQ nos permite seleccionar elementos desde una colección. Esta selección se realiza de acuerdo a las características de los elementos de datos contenidos dentro de la colección [1].

Veamos la secuencia elemental para consultar/seleccionar datos en una colección usando LINQ [1]:
  1. Iniciar con la palabra clave from [4] de LINQ.
  2. Determinar las condiciones de consulta con la palabra clave where [5].
  3. A través de la palabra clave select [6], indicar cuál valor debe ser agregado al resultado.
  4. Con orderby [7] especificamos el orden para nuestra colección de resultados.
El tipo de dato para la instancia devuelta por una consulta LINQ es IEnumerable [8]. La instancia IEnumerable enumera los elementos de la colección o el arreglo de acuerdo al resultado generado por la condición o criterio de búsqueda. Para enumerar cada elemento del resultado exponemos al objeto IEnumerable en un ciclo foreach.

Veamos un ejemplo de línea de código en el que seleccionamos el primer carácter para cualquier elemento del arreglo de cadena de caracteres que supere los 4 caracteres. El resultado lo ordenamos con base en la longitud:

IEnumerable<char> resultado = from e in arregloString where e.Length > 4 orderby e.Length select e[0];

De igual manera, una consulta puede ser escrita usando expresiones lambda (tema de futuros artículos); éstas se conjugan con los métodos disponibles en los tipos de colecciones: clases y arreglos. El equivalente a la sentencia anterior, utilizando este enfoque es:

IEnumerable<char> resultado = arregloString.Where( e => e.Length >4).OrderyBy(e => e.Length).Select(e => e[0]);

Cuando se trata de paralelismo, LINQ también ofrece una maquinaria para paralelizar una consulta: partición en múltiples hilos para el procesamiento de los datos en parálelo. La extensión de LINQ para consultas en paralelo se conoce como PLINQ. Este tipo enfoque es idóneo para ambientes en donde los datos a procesar pasan cantidades exorbitantes. Veamos el equivalente de la primera demostración utilizando este enfoque:

IEnumerable<char> resultado = from e in arregloString.AsParallel() where e.Length > 4 orderby e.Length select e[0];

3.1 La clausula from

Veamos algunos ejemplos de uso de la palabra from en algunas consultas:

Archivo UsoFrom.cs:

> Prueba de ejecución.

Resultado:


4 1 3 2 0

3.2 La clausula where

Echemos un vistazo al uso de la clausula where:

Archivo UsoWhere.cs:

> Prueba de ejecución.

Resultado:

4 8 6 2 0

3.3 La clausula select

¿Cómo funciona la clausula select? Aquí un ejemplo simple de uso:

Archivo UsoSelect.cs:

> Prueba de ejecución.

Resultado:

97 92 81

4. Práctica: Código Fuente C#

En este ejemplo vamos a crear una clase personalizada. La lista genérica contendrá elementos de este tipo de objeto nuevo, y luego crearemos expresiones de selección estándar y lambda:

Archivo FrutaLinq.cs



> Prueba de ejecución.

Resultado:
Resultado ejecución ejemplo en LINQ: FrutaLinq.
Figura 1. Resultado ejecución ejemplo en LINQ: FrutaLinq.

5. Conclusiones

Aprendimos que LINQ es un lenguaje de consultas muy poderoso y expresivo que está diseñado para buscar/seleccionar datos desde diferentes fuentes: arreglos, colecciones, conjunto de datos ADO.NET, bases de datos, documentos XML. Exploramos las clausulas de composición de consultas: from, where, y select. (En futuros artículos me extenderé en este tema tan llamativo.)

Glosario

  • Arreglo
  • Colección
  • Conjunto de datos
  • Consulta
  • LINQ
  • SQL
  • XML

Literatura & Enlaces

[1]: Visual C# 2010 Recipes by Allen Jones and Adam Freeman. Copyright 2010 Allen Jones and Adam Freeman, 978-1-4302-2525-6.
[2]: LINQ (Language-Integrated Query) - http://msdn.microsoft.com/en-us/library/bb397926.aspx
[3]: Language Integrated Query - Wikipedia, the free encyclopedia - http://en.wikipedia.org/wiki/Language_Integrated_Query
[4]: from clause (C# Reference) - http://msdn.microsoft.com/en-us/library/bb383978.aspx
[5]: where clause (C# Reference) - http://msdn.microsoft.com/en-us/library/vstudio/bb311043(v=vs.110).aspx
[6]: select clause (C# Reference) - http://msdn.microsoft.com/en-us/library/vstudio/bb384087(v=vs.100).aspx
[7]: orderby clause (C# Reference) - http://msdn.microsoft.com/en-us/library/bb383982.aspx
[8]: IEnumerable Interface (System.Collections) - http://msdn.microsoft.com/en-us/library/system.collections.ienumerable(v=vs.110).aspx
[9]: Parallel LINQ (PLINQ) - http://msdn.microsoft.com/en-us/library/dd460688(v=vs.110).aspx


M

No hay comentarios:

Publicar un comentario

Envíe sus comentarios, dudas, sugerencias, críticas. Gracias.