web-dev-qa-db-fra.com

LINQ Lambda, Grouper par avec liste

J'ai du mal à trouver la bonne syntaxe pour accomplir les tâches suivantes:

Est-il possible avec LINQ (expression lambda) d’utiliser les données .GroupBy et au lieu d’utiliser l’habituel .Sum () ou .Count (), je souhaite que les données obtenues constituent une liste de Int.

J'ai défini ma propre classe nommée: Filter_IDs. Son constructeur a besoin de deux paramètres:

public int? type; // Represents the object_type column from my database
public List<int?> objects; // Represents the object_id column from my database

Je veux charger les données de ma base de données dans cet objet. La requête LINQ suivante doit générer une liste d'identificateurs de filtre:

La requête LINQ suivante doit générer une liste d'identificateurs de filtre:

List<Filter_IDs> filterids = ef.filterLine
        .GroupBy(fl => fl.objectType)
    .Select(fl => new Filter_IDs { type = fl.Key, objects = fl.Select(x => x.object_id).ToList() })
    .ToList();

L'utilisation de cette requête ne génère aucune erreur de construction, mais une exception 'NotSupportedException' sous RunTime.

La base de données ressemble à ceci pour vous donner une meilleure compréhension des données:

http://d.pr/i/mnhq+ (image droplr)

Merci d'avance, Gerben

8
G Versluis

Je pense que le problème est que la base de données n'est pas en mesure d'appeler ToList dans la sélection, ni de créer un nouveau Filter_ID.

Essayez quelque chose comme ça:

List<Filter_IDs> filterids = ef.filterLine.Select(o => new { objectType = o.objectType, object_id=o.object_id})
    .GroupBy(fl => fl.objectType).ToList()
    .Select(fl => new Filter_IDs { type = fl.Key, objects = fl.Select(x => x.object_id).ToList() })
    .ToList();
11
Kek

Peut-être que tu veux

IList<Filter_IDs> filterIds = ef.filterline
    .Select(fl => fl.objectType).Distinct()
    .Select(ot => new Filter_IDs
        {
            type = ot,
            objects = ef.filterline
                          .Where(fl => fl.objectType == ot)
                          .Select(fl =>objectType)
                          .ToList()
        }).ToList();

Obtenez la liste distincte objectType et utilisez-la pour sous-interroger chaque liste de object_id.

Cependant, il me semble plus efficace de simplement énumérer les valeurs dans l’ordre,

var results = new List<Filter_IDs>();
var ids = new List<int>();
var first = true;
int thisType;

foreach (var fl in ef.filterLines
                       .OrderBy(fl => fl.objectType)
                       .ThenBy(fl => fl.object_Id))
{
    if (first)
    {
        thisType = fl.objectType;
        first = false;
    }
    else
    {
        if (fl.objectType == thisType)
        {
            ids.Add(fl.object_Id);
        }
        else
        {
           results.Add(new Filter_IDs
                {
                    Type = thisType,
                    objects = ids
                });
           thisType = fl.objectType;
           ids = new List<int>();   
        }
    }    
}
1
Jodrell

Vous pouvez utiliser GroupBy côté client:

List<Filter_IDs> filterids = ef.filterLine
        .Select(fl=>new {fl.ObjectType, fl.object_id})
        .AsEnumerable()
        .GroupBy(fl => fl.objectType)
    .Select(fl => new Filter_IDs { type = fl.Key, objects = fl.Select(x => x.object_id).ToList() })
    .ToList();
0
Kirill Bestemyanov