2011-12-22 23 views
8

tengo IEnumerable<MyData> que contiene los datos siguientesLINQ consulta para seleccionar registros superiores

Fruits | Name | Quantity | 
__________________________ 
Mango | Jay | 10 | 
__________________________ 
Apple | Jay | 16 | 
__________________________ 
Grapes| Jay | 12 | 
__________________________ 
Mango | Raj | 11 | 
__________________________ 
Apple | Raj | 20 | 
__________________________ 
Grapes| Raj | 3  | 
__________________________ 
Mango | Vik | 20 | 
__________________________ 
Apple | Vik | 15 | 
__________________________ 

necesito para seleccionar de LINQ parte superior de dos cantidad según nombre como

Jay (10+16+12) = 38 
Raj (11+20+3) = 34 
Vik (20+15) = 35 

Jay y Vik tienen dos cantidad superior suma así que necesito estos registros

Fruits | Name | Quantity | 
__________________________ 
Mango | Jay | 10 | 
__________________________ 
Apple | Jay | 16 | 
__________________________ 
Grapes| Jay | 12 | 
__________________________ 
Mango | Vik | 20 | 
__________________________ 
Apple | Vik | 15 | 
__________________________ 
+0

Así sólo para aclarar. ¿Desea sumar las cantidades por nombre, buscar los dos nombres principales y luego seleccionar los registros con esos nombres? – Ray

+0

@Ray: sí, claro. –

Respuesta

11

suena como usted puede ser que desee algo como:

var query = from item in collection 
      group item by item.Name into g 
      orderby g.Sum(x => x.Quantity) descending 
      select g; 
var topTwo = query.Take(2); 

que se llevará a los primeros dos grupos , por lo que tendría que utilizar como:

foreach (var group in topTwo) 
{ 
    Console.WriteLine("Name: {0}", group.Key); 
    foreach (var item in group) 
    { 
     Console.WriteLine(" {0}: {1}", item.Fruits, item.Quantity); 
    } 
} 
+1

¡Gracias! mi problema ahora está resuelto –

+1

¿No debería ser ordenado por desc? – Ray

+2

@Ray: Sí, lo solucionó Govind; gracias :) :) –

0

Pruebe lo siguiente:

var topTwo = myData.GroupBy(d => d.Name).OrderByDescending(g => g.Sum(d => d.Quantity)).TakeWhile((data,index) => index < 2).SelectMany(g => g); 
4

Algo como esto trabajaría.

private static IEnumerable<MyData> GetTop2Names(IEnumerable<MyData> data) 
{ 
    var top2 = data.GroupBy(d => d.Name) 
        .OrderByDescending(g => g.Sum(d => d.Quantity)) 
        .Take(2) 
        .Select(g => g.Key); 
    return data.Where(d => top2.Contains(d.Name)); 
} 

Paso a paso

  1. Grupo por Nombre (ya que eso es lo que estás sumando)
  2. clasificar por la suma de las cantidades
  3. Tomar la parte superior 2 nombres
  4. Seleccionar los artículos de la lista original que coinciden con esos nombres.
+0

+1 muy bonito ... muchas gracias –

0

debería tener este aspecto:

IEnumerable<MyData> source = new List<MyData>(); 
var names = source 
    .GroupBy(item => item.Name) 
    .ToDictionary(item => item.Key, item => item.Sum(i => i.Quantity)) 
    .OrderByDescending(item => item.Value) 
    .Select(item => item.Key) 
    .Take(2); 

var result = source.Where(item => names.Contains(item.Name)); 
Cuestiones relacionadas