jueves, 18 de diciembre de 2014

Cómo Hacer un Group By de Objetos usando Linq

En éste artículo veremos como crear un group by usando linq en vb.net.

Para este ejemplo usaremos la función agruparDatos que recibe por parámetro un DataTable, ya que para este ejemplo usaremos un DataTable


Public Function agruparDatos(ByVal dt As DataTable) As DataTable
        //Declaramos nuestro objeto linq donde en este caso sera un grupo por el campo Fecha
       //y los campos en el select hacemos un sum,avg,max para hacer los calculos

        Dim obj =
                   From row
                   In dt
                   Group row By Fecha = row.Field(Of Date)("Fecha")
        Into Merma = Group
                Select New With
                  {
                      Key Fecha,

                        .Monto= Merma.Sum(Function(r) r.Field(Of Integer)("Monto")),
                        .SubTotal= Merma.Sum(Function(r) r.Field(Of Decimal)("SubTotal")),
                        .Total= Merma.Sum(Function(r) r.Field(Of Integer)("Total")),

                        .Cantidad= Merma.Sum(Function(r) r.Field(Of Decimal)("Cantidad")),
                        .Diferencia= Merma.Sum(Function(r) r.Field(Of Decimal)("Diferencia")),
                        .Porcentaje= Merma.Max(Function(r) r.Field(Of Decimal)("Porcentaje")),
                        .Promedio= Merma.Avg(Function(r) r.Field(Of Decimal)("Promedio"))
                        }

        //Declaramos nuestro nuevo dt y colonamos la estructura del dt del parámetro
        Dim dt2 As DataTable = dt.Clone
       
       //Recorremos el objeto e insertamos las filas al nuevo dt
        For i = 0 To obj.Count - 1
            Dim dr As DataRow = dt2.NewRow
            dr("ID") = i + 1
            dr("Fecha") = obj(i).Fecha
            dr("Monto") = obj(i).Monto
            dr("SubTotal") = obj(i).SubTotal
            dr("Total") = obj(i).Total
            dr("Cantidad") = obj(i).Cantidad
            dr("Diferencia") = Math.Abs(obj(i).Diferencia)
            dr("Porcentaje") = obj(i).Porcentaje
            dr("Promedio") = obj(i).Promedio
            dr("Calculado") = ((dr("Monto") - dr("Diferencia")) / dr("Total")) * 100


        Next

       //actualizamos el nuevo dt para que se guarden las nuevas filas agregadas
        dt2.AcceptChanges()

       
        Return dt2
    End Function

1 comentario:

  1. Buenas tardes.
    Justo estoy buscando este tipo de información, la verdad que no he trabajado con LINQ, pero ahora estoy haciendo y mi pregunta es ¿como mostraría un campo string dentro del select new, digamos si quisiera mostrar el nombre del cliente u otro dato que crea necesario a parte de los calculados.?

    ResponderBorrar