Entity Framework: Efficacement regroupement par mois
J'ai fait un peu de recherche sur ce sujet, et le meilleur que j'ai trouvé pour l'instant est d'utiliser un Asenumerable sur l'ensemble du jeu de données, de sorte que le filtrage se produit dans linq to objects, plutôt que sur la DB. J'utilise la dernière EF.
Mon travail (mais très lent) code:
var trendData =
from d in ExpenseItemsViewableDirect.AsEnumerable()
group d by new {Period = d.Er_Approved_Date.Year.ToString() + "-" + d.Er_Approved_Date.Month.ToString("00") } into g
select new
{
Period = g.Key.Period,
Total = g.Sum(x => x.Item_Amount),
AveragePerTrans = Math.Round(g.Average(x => x.Item_Amount),2)
};
Cela me donne mois dans le format AAAA-MM, ainsi que le montant total et montant moyen. Cependant, il faut plusieurs minutes à chaque fois.
Mon autre solution est de faire une mise à jour de la requête en SQL j'ai donc un AAAAMM champ de groupe en mode natif, par. La modification de la DB n'est pas une solution facile, cependant toutes les suggestions seraient appréciées.
Le fil, j'ai trouvé le code ci-dessus idée (http://stackoverflow.com/questions/1059737/group-by-weeks-in-linq-to-entities) mentionne " en attente jusqu'à ce que .NET 4.0'. Est-il quelque chose récemment introduite qui aide dans cette situation?
Vous devez vous connecter pour publier un commentaire.
La raison de cette mauvaise performance est que l'ensemble de la table est chargée en mémoire (AsEnumerable()). Vous pouvez groupe puis par Année et par Mois, à l'instar de ce
modifier
La requête d'origine, à partir de ma réponse, était en train de faire une concaténation entre un int et un string, ce qui n'est pas traduisible en EF dans les instructions SQL. Je pourrais utiliser SqlFunctions classe, mais la requête qu'il devient laid. J'ai donc ajouté AsEnumerable() après le regroupement est fait, ce qui signifie que EF exécuter la requête du groupe sur le serveur, obtiendrez l'année, le mois, etc, mais la coutume de projection est faite sur des objets (ce qui suit après AsEnumerable()).
Quand il s'agit de groupe par mois, je préfère le faire de cette façon:
Qu'il continue de type datetime dans le groupement résultat.
GroupBy(g=>new{g.DateTime.Year, g.DateTime.Month}
De même à ce cryss écrit, je suis en train de faire la suite pour l'EF. Notez que nous avons à utiliser EntityFunctions pour être en mesure d'appeler tous les DB fournisseurs pris en charge par EF. SqlFunctions ne fonctionne que pour SQLServer.
Un avant-goût de SQL généré (à partir d'un schéma similaire):