miércoles, 10 de diciembre de 2014

Operadores de Consulta





Dentro del universo de LinQ, tenemos dos formas diferentes de realizar las llamadas y hacer uso de nuestros métodos de extensores de IEnumerable<T>, la primera es haciendo uso de las Expresiones Lambda, que vendría a representar un uso cotidiano de cualquier método extensor, y la segunda es utilizando el llamado azúcar sintáctico (formato de consulta) y que nos permite realizar una consulta de manera muy similar a como realizaríamos una llamada en el lenguaje SQL.


Es importante señalar que hay algunas opciones que no están disponibles dentro del formato de consulta, aunque son las mínimas, y que iremos viendo según vayamos estudiando los operadores (métodos extensores).




Recuerda que aquí tienes el indice de todos los posts del Curso de LinQ.



Vamos a ver unos ejemplos de cada uno de los tipos.


Expression Lambda:


var resultado = ColeccionClientes
                .Where(fila => fila.Contains("a"))
                .OrderBy(fila => fila.Nombre)
                .Select(unaFila => unaFila);


Expresión de consulta:

var resultado = from fila in ColeccionClientes
                where fila.Nombre.Contains("a")
                orderby fila.Nombre
                select fila;





Dentro de las Expresiones de Consulta, es curioso destacar que la cláusula Select, va situada justamente al contrario que en SQL, al final en vez de al principio, esto es así, ya que es la única manera de que el intellisense pueda conocer los campos de tipo a seleccionar.



¿Qué formato de consulta usar?

Como en muchas de estas cuestiones de la vida y de la programación, esto es cuestión de gustos. Yo personalmente creo que el formato de consulta es mucho más sencillo de leer, sobre todo cuando las consultas son un poco más complejas (Joins, groups by, etc) y que esto hace que cualquier otro desarrollador con conocimientos de SQL, pueda leerlo con más facilidad, todo esto lo digo en el sentido estricto, porque para mí se me hace bastante más liviano tratar con lambda, por la velocidad de escritura y por su versatilidad, pero no dejo de admitid su opacidad, ya que en muchas ocasiones no son tabuladas como deberían y se convierten en chorrazos ilegibles.

El formato de consulta, nos permite utilizar la cláusula let o into, que veremos más adelante y que nos permitirá hacer que nuestro código sea más legible y más eficiente.

A favor de las Lambdas, tengo que decir que su aparición en el framework, cada vez es más frecuente, y que escribirlas y dominarlas te hace tener un conocimiento mucho más profundo del lenguaje.


En muchas ocasiones veremos que se puede utilizar un mix de las mismas, algo así:

var resultado = from fila in ColeccionClientes.Where(f => f.Contains("a"))
                orderby fila.Nombre
                select fila;



System.Linq

Este es el espacio de nombres donde está definida toda la información de linQ. Posteriormente en los siguientes posts estudiaremos todos los métodos de extensión definidos en la clase System.Linq.Enumerable, formado por más de 40 métodos:


Consulta de nombres de métodos extensores utilizando LinQ:

static void Main(string[] args)
{
    var metodosLinQ = typeof(System.LinqEnumerable).GetMethods()
                        .Where(m => m.IsDefined(typeof(ExtensionAttribute), false))
                        .Select(a => a.Name)
                        .OrderBy(a => a)
                        .Distinct().ToList();
 
    metodosLinQ.ForEach(m => Console.WriteLine(m));
 
    Console.Read();
}


Resultado:




Los iremos viendo en grupos según tipología.


Es importante señalar como hemos indicado arriba que estos métodos extensores son aplicables al tipo IEnumerable<T> (Enumeradores) y que devuelven todos, otra secuencia de Enumeradores del mismo tipo.