LINQ Group By with multiple fields

2

I'm trying to return fields after a join between collections, but I'm getting the following error:

  

foreach statement can not operate on variables of type   'AnonymousType # 1' because 'AnonymousType # 1' does not contain a public   definition for 'GetEnumerator'

var lst = from p in Produto.produtos
        join c in Produto.categorias
        on p.IdCategoria equals c.IdCategoria
        group p by new { c.IdCategoria, c.Categoria }
            into g
            orderby g.Key.Categoria
            select new { ID = g.Key.IdCategoria, CategoriaNome = g.Key.Categoria, TotalItem = g.Count() };

foreach (var categ in lst)
{
    Console.WriteLine("ID: {0}, Categoria: {1}, Total Item: {2}", categ.ID, categ.CategoriaNome, categ.TotalItem);
    foreach (var item in categ)
    {
        Console.WriteLine("\t\tID: {0}, Produto: {1}", item.IdProduto, item.Produto); <b>// Linha com o Erro</b>
    }
}
    
asked by anonymous 03.09.2015 / 22:41

2 answers

4

This returns List<n'> , where n' is an anonymous type:

var lst = from p in Produto.produtos
        join c in Produto.categorias
        on p.IdCategoria equals c.IdCategoria
        group p by new { c.IdCategoria, c.Categoria }
            into g
            orderby g.Key.Categoria
            select new { ID = g.Key.IdCategoria, CategoriaNome = g.Key.Categoria, TotalItem = g.Count() };

This iterates over List<n'> :

foreach (var categ in lst)
{ ... }

And this you try to iterate over n' that is not "iterable":

foreach (var item in categ)
{ ... }

So the error.

EDIT

According to your comment in the other answer, you want to group by category. So, modify your sentence to:

var lst = from p in Produto.produtos
    join c in Produto.categorias
    on p.IdCategoria equals c.IdCategoria
    group p by new { c.IdCategoria, c.Categoria }
        into g
        orderby g.Key.Categoria;

The first foreach looks like this:

foreach (var categ in lst)
{
    Console.WriteLine("ID: {0}, Categoria: {1}, Total Item: {2}", categ.Key.IdCategoria, categ.Key.Categoria, categ.Count());
    ...

The second stays the same:

foreach (var item in categ)
{
    Console.WriteLine("\t\tID: {0}, Produto: {1}", item.IdProduto, item.Produto);
}
    
03.09.2015 / 22:45
0

Let's change everything.

var lstCategorias = (from p in Produto.categorias select p).ToList();
foreach (var categoria in lstCategorias)
{
     var lstProdutos = (from p in Produto.produtos where p.IdCategoria=categoria.ID select p).ToList();
    Console.WriteLine("ID: {0}, Categoria: {1}, Total Item: {2}", categoria.ID, categoria.CategoriaNome, lstProdutos.Count);
    foreach (var item in lstProdutos)
    {
        Console.WriteLine("\t\tID: {0}, Produto: {1}", item.IdProduto, item.Produto); <b>// Linha com o Erro</b>
    }
}

Explaining:

Getting the categories

var lstCategorias = (from p in Produto.categorias select p).ToList();

Iterating with foreach

foreach (var categoria in lstCategorias)

Filtering Category Products within foreach

var lstProdutos = (from p in Produto.produtos where p.IdCategoria=categoria.ID select p).ToList();

Printing the result

Console.WriteLine("ID: {0}, Categoria: {1}, Total Item: {2}", categoria.ID, 
categoria.CategoriaNome, lstProdutos.Count);

New foreach to list products in category

foreach (var item in lstProdutos)
{
    Console.WriteLine("\t\tID: {0}, Produto: {1}", item.IdProduto, item.Produto); <b>// Linha com o Erro</b>
    
03.09.2015 / 22:52