Cela peut sembler boiteux, mais je n'ai pas pu trouver une très bonne explication Aggregate
.
Bon signifie court, descriptif, complet avec un petit exemple clair.
La définition la plus simple à comprendre de Aggregate
est qu'il effectue une opération sur chaque élément de la liste en tenant compte des opérations précédentes. C'est-à-dire qu'il exécute l'action sur le premier et le deuxième élément et fait avancer le résultat. Ensuite, il opère sur le résultat précédent et le troisième élément et continue. etc.
Exemple 1. Additionner des nombres
var nums = new[]{1,2,3,4};
var sum = nums.Aggregate( (a,b) => a + b);
Console.WriteLine(sum); // output: 10 (1+2+3+4)
Cela ajoute 1
et 2
à faire 3
. Ajoute ensuite 3
(résultat du précédent) et 3
(élément suivant dans la séquence) à faire 6
. Ajoute ensuite 6
et 4
à faire 10
.
Exemple 2. créer un csv à partir d'un tableau de chaînes
var chars = new []{"a","b","c", "d"};
var csv = chars.Aggregate( (a,b) => a + ',' + b);
Console.WriteLine(csv); // Output a,b,c,d
Cela fonctionne de la même manière. Concaténer a
une virgule et b
faire a,b
. Concatène ensuite a,b
avec une virgule et c
à faire a,b,c
. etc.
Exemple 3. Multiplication de nombres à l'aide d'une graine
Pour être complet, il y a une surcharge de ce Aggregate
qui prend une valeur de départ.
var multipliers = new []{10,20,30,40};
var multiplied = multipliers.Aggregate(5, (a,b) => a * b);
Console.WriteLine(multiplied); //Output 1200000 ((((5*10)*20)*30)*40)
Tout comme les exemples ci-dessus, cela commence par une valeur de 5
et la multiplie par le premier élément de la séquence 10
donnant un résultat de 50
. Ce résultat est reporté et multiplié par le nombre suivant de la séquence 20
pour donner un résultat de 1000
. Cela continue à travers les 2 éléments restants de la séquence.
Exemples en direct: http://rextester.com/ZXZ64749
Docs: http://msdn.microsoft.com/en-us/library/bb548651.aspx
Addenda
L'exemple 2 ci-dessus utilise la concaténation de chaînes pour créer une liste de valeurs séparées par une virgule. Il s'agit d'une manière simpliste d'expliquer l'utilisation de Aggregate
laquelle était l'intention de cette réponse. Cependant, si vous utilisez cette technique pour créer réellement une grande quantité de données séparées par des virgules, il serait plus approprié d'utiliser un StringBuilder
, et cela est entièrement compatible avec l' Aggregate
utilisation de la surcharge prédéfinie pour lancer le StringBuilder
.
var chars = new []{"a","b","c", "d"};
var csv = chars.Aggregate(new StringBuilder(), (a,b) => {
if(a.Length>0)
a.Append(",");
a.Append(b);
return a;
});
Console.WriteLine(csv);
Exemple mis à jour: http://rextester.com/YZCVXV6464
[1,2,3,4]
sera-t-il[3,3,4]
alors[6,4]
et enfin[10]
. Mais au lieu de renvoyer un tableau d'une seule valeur, vous obtenez simplement la valeur elle-même.TakeWhile
puis unAggregate
- c'est le devoir des extensions Enumerable - ils sont facilement chaînables. Vous vous retrouvez donc avecTakeWhile(a => a == 'a').Aggregate(....)
. Voir cet exemple: rextester.com/WPRA60543var csv = string.Join(",", chars)
(pas besoin d'agrégat ou de constructeurs de chaînes) - mais oui, je sais que l'objectif de la réponse était de donner un exemple d'utilisation d'agrégat, donc c'est cool. Mais je voulais quand même mentionner qu'il n'est pas recommandé de simplement joindre des chaînes, il y a déjà une méthode dédiée à cela ....var biggestAccount = Accounts.Aggregate((a1, a2) => a1.Amount >= a2.Amount ? a1 : a2);
Cela dépend en partie de la surcharge dont vous parlez, mais l'idée de base est:
(currentValue, sequenceValue)
en(nextValue)
currentValue = nextValue
currentValue
Vous pouvez trouver le
Aggregate
message dans ma série Edulinq utile - il comprend une description plus détaillée (y compris les différentes surcharges) et les implémentations.Un exemple simple utilise
Aggregate
comme alternative àCount
:Ou peut-être en additionnant toutes les longueurs de chaînes dans une séquence de chaînes:
Personnellement, je trouve rarement
Aggregate
utile - les méthodes d'agrégation "sur mesure" sont généralement assez bonnes pour moi.la source
L' agrégat super court fonctionne comme le pli en Haskell / ML / F #.
Légèrement plus long .Max (), .Min (), .Sum (), .Average () tous les itérations sur les éléments dans une séquence et les agrège en utilisant la fonction d'agrégation respective. .Aggregate () est un agrégateur généralisé en ce qu'il permet au développeur de spécifier l'état de départ (aka seed) et la fonction d'agrégation.
Je sais que vous avez demandé une brève explication, mais je me suis dit que d'autres ont donné quelques brèves réponses, je me suis dit que vous seriez peut-être intéressé par une réponse un peu plus longue
Version longue avec code Une façon d'illustrer ce que cela pourrait être de montrer comment vous implémentez l' exemple d'écart-type une fois en utilisant foreach et une fois en utilisant .Aggregate. Remarque: Je n'ai pas priorisé les performances ici, donc je répète inutilement plusieurs fois la collection
D'abord une fonction d'aide utilisée pour créer une somme de distances quadratiques:
Échantillonnez ensuite l'écart type à l'aide de ForEach:
Puis une fois en utilisant .Aggregate:
Notez que ces fonctions sont identiques, sauf pour la façon dont sumOfQuadraticDistance est calculé:
Contre:
Ce que fait .Aggregate, c'est qu'il encapsule ce modèle d'agrégateur et je m'attends à ce que l'implémentation de .Aggregate ressemble à ceci:
L'utilisation des fonctions d'écart standard ressemblerait à ceci:
A mon humble avis
Est-ce que .Aggregate aide à la lisibilité? En général, j'aime LINQ parce que je pense que .Where, .Select, .OrderBy et ainsi de suite aident grandement la lisibilité (si vous évitez les .Selects hiérarchiques en ligne). L'agrégat doit être dans Linq pour des raisons d'exhaustivité, mais personnellement, je ne suis pas convaincu que l'agrégat ajoute de la lisibilité par rapport à un foreach bien écrit.
la source
SampleStandardDeviation_Aggregate()
etSampleStandardDeviation_ForEach()
ne peuvent pas l'êtreprivate
(par défaut en l'absence d'un qualificatif d'accès), elles auraient donc dû être accumulées parpublic
ouinternal
, il me sembleUne image vaut mieux que mille mots
Enumerable.Aggregate a trois surcharges:
Surcharge 1:
Exemple:
Cette surcharge est simple, mais elle présente les limitations suivantes:
sinon la fonction lancera un
InvalidOperationException
.Surcharge 2:
Exemple:
Cette surcharge est plus générale:
bIn
).dans ce cas, la fonction donnera la valeur de départ comme résultat.
Surcharge 3:
La troisième surcharge n'est pas très utile IMO.
La même chose peut être écrite de manière plus succincte en utilisant la surcharge 2 suivie d'une fonction qui transforme son résultat.
la source
Aggegate
.net qui prend unFunc<T, T, T>
.seed
, applique la fonction d'accumulateur N -1 fois; tandis que les autres (qui les surcharges ne prennent aseed
) appliquent la fonction de l' accumulateur N fois.L'agrégat est essentiellement utilisé pour regrouper ou résumer les données.
Selon MSDN "Aggregate Function Applique une fonction d'accumulateur sur une séquence."
Exemple 1: ajoutez tous les nombres dans un tableau.
* important: la valeur agrégée initiale par défaut est l'élément 1 dans la séquence de collecte. c'est-à-dire que la valeur initiale totale de la variable sera 1 par défaut.
explication variable
total: il contiendra la valeur de synthèse (valeur agrégée) renvoyée par le func.
nextValue: c'est la valeur suivante dans la séquence du tableau. Cette valeur est ensuite ajoutée à la valeur agrégée, c'est-à-dire au total.
Exemple 2: ajoutez tous les éléments d'un tableau. Définissez également la valeur initiale de l'accumulateur pour commencer à ajouter à partir de 10.
explication des arguments:
le premier argument est l'initiale (valeur de départ, c'est-à-dire la valeur de départ) qui sera utilisée pour commencer l'addition avec la valeur suivante dans le tableau.
le deuxième argument est un func qui est un func qui prend 2 int.
1. total: cela sera le même qu'avant la valeur de résumé (valeur agrégée) renvoyée par la fonction après le calcul.
2.nextValue:: il s'agit de la valeur suivante dans la séquence du tableau. Cette valeur est ensuite ajoutée à la valeur agrégée, c'est-à-dire au total.
Le débogage de ce code vous permettra également de mieux comprendre le fonctionnement des agrégats.
la source
J'ai beaucoup appris de la réponse de Jamiec .
Si le seul besoin est de générer une chaîne CSV, vous pouvez essayer ceci.
Voici un test avec 1 million de cordes
Le code source est ici
la source
En plus de toutes les bonnes réponses ici déjà, je l'ai également utilisé pour parcourir un élément à travers une série d'étapes de transformation.
Si une transformation est implémentée en tant que
Func<T,T>
, vous pouvez ajouter plusieurs transformations à aList<Func<T,T>>
et utiliserAggregate
pour parcourir une instance deT
chaque étape.Un exemple plus concret
Vous voulez prendre une
string
valeur et la parcourir à travers une série de transformations de texte qui pourraient être construites par programme.Cela créera une chaîne de transformations: Supprimer les espaces de début et de fin -> supprimer le premier caractère -> supprimer le dernier caractère -> convertir en majuscules. Les étapes de cette chaîne peuvent être ajoutées, supprimées ou réorganisées selon les besoins, pour créer le type de pipeline de transformation requis.
Le résultat final de ce pipeline spécifique, c'est qu'il
" cat "
devient"A"
.Cela peut devenir très puissant une fois que vous réalisez que cela
T
peut être n'importe quoi . Cela pourrait être utilisé pour les transformations d'images, comme les filtres, en utilisantBitMap
comme exemple;la source
La méthode d'agrégation est une méthode d'extension pour les collections génériques. La méthode d'agrégation applique une fonction à chaque élément d'une collection. Non seulement applique une fonction, mais prend son résultat comme valeur initiale pour la prochaine itération. Ainsi, en conséquence, nous obtiendrons une valeur calculée (min, max, moyenne ou autre valeur statistique) à partir d'une collection.
Par conséquent, la méthode Aggregate est une forme d'implémentation sûre d'une fonction récursive.
Sûr , car la récursion va itérer sur chaque élément d'une collection et nous ne pouvons pas obtenir de suspension de boucle infinie par une condition de sortie incorrecte. Récursif , car le résultat de la fonction actuelle est utilisé comme paramètre pour le prochain appel de fonction.
Comment ça fonctionne:
qui fait la même chose que cette fonction:
la source
Il s'agit d'une explication sur l'utilisation
Aggregate
sur une API Fluent telle que Linq Sorting.et voyons que nous voulons implémenter une fonction de tri qui prend un ensemble de champs, c'est très facile à utiliser
Aggregate
au lieu d'une boucle for, comme ceci:Et nous pouvons l'utiliser comme ceci:
la source
Tout le monde a donné son explication. Mon explication est comme ça.
La méthode d'agrégation applique une fonction à chaque élément d'une collection. Par exemple, ayons la collection {6, 2, 8, 3} et la fonction Add (opérateur +) qu'elle fait (((6 + 2) +8) +3) et renvoie 19
Dans cet exemple, la méthode nommée Add est passée au lieu de l'expression lambda.
la source
Une définition courte et essentielle pourrait être celle-ci: la méthode d'extension Linq Aggregate permet de déclarer une sorte de fonction récursive appliquée sur les éléments d'une liste, dont les opérandes sont deux: les éléments dans l'ordre dans lequel ils sont présents dans la liste, un élément à la fois, et le résultat de l'itération récursive précédente ou rien si ce n'est pas encore la récursivité.
De cette façon, vous pouvez calculer la factorielle des nombres ou concaténer des chaînes.
la source
Agrégat utilisé pour additionner des colonnes dans un tableau entier multidimensionnel
Select with index est utilisé dans la fonction Aggregate pour additionner les colonnes correspondantes et renvoyer un nouveau tableau; {3 + 2 = 5, 1 + 4 = 5, 7 + 16 = 23, 8 + 5 = 13}.
Mais compter le nombre de vrais dans un tableau booléen est plus difficile car le type accumulé (int) diffère du type source (bool); ici une graine est nécessaire pour utiliser la deuxième surcharge.
la source