diff --git a/LinqStudy.Test/LinqToObject/AggregationTest.cs b/LinqStudy.Test/LinqToObject/AggregationTest.cs
new file mode 100644
index 0000000..75fd773
--- /dev/null
+++ b/LinqStudy.Test/LinqToObject/AggregationTest.cs
@@ -0,0 +1,154 @@
+using System;
+using System.Collections.Generic;
+using System.Text;
+using System.Linq;
+
+using Xunit;
+
+namespace LinqStudy.Test.LinqToObject
+{
+ ///
+ /// 聚合操作符:所有聚合操作是“立即执行”,不再一一测试。
+ ///
+ public class AggregationTest
+ {
+ #region Aggregate
+
+ ///
+ /// Aggregate:自定义聚合计算,是聚合计算的“基础”。所有聚合操作均是“立即执行”。
+ /// 选择序列中的第一项(或自定义参数)为初始“聚合项”,“聚合项”作为输入项与序列中的下一项进行“聚合”操作,返回新的“聚合项”;
+ /// 新的“聚合项”与下一项继续“聚合”,直到序列中所有项都完成“聚合操作”,返回最后的“聚合项”。
+ ///
+ [Fact]
+ public void Aggregate_default_Test()
+ {
+ List peoples = new List()
+ {
+ new Person(){ Id=1, Name="张三丰", Age=230},
+ new Person(){ Id=2, Name="小龙女", Age=28},
+ new Person(){ Id=3, Name="银花公主", Age=16},
+ new Person(){ Id=4, Name="杨过", Age=32},
+ //new Person(){ Id=5, Name="东方不败", Age=86},
+ //new Person(){ Id=6, Name="金轮法王", Age=64},
+ //new Person(){ Id=7, Name="周伯通", Age=98},
+ //new Person(){ Id=8, Name="洪七公", Age=97},
+ //new Person(){ Id=9, Name="郭靖", Age=63},
+ //new Person(){ Id=10, Name="黄蓉", Age=59},
+ };
+
+ //默认第一项作为"初始聚合项",即首次聚合操作,第一项作为“聚合项”输入与第二项聚合,一共“聚合”3次。
+ //第1次:第1项作为“聚合项”与第2项“聚合”,返回新“聚合项”作为下次“聚合操作的”的“聚合项”参数;
+ //第2次:第1次返回的“聚合项”与第3项“聚合”,返回新“聚合项”;
+ //第3次:第2次返回的“聚合项”与第4项“聚合”,返回新“聚合项”;
+ // 由于第4项是最后一项,整个“聚合操作”结束,返回本次“聚合项”作为最后的输出。
+ var agg = peoples.Aggregate
+ (
+ (aggregateItem, next) =>
+ {
+ //把当前元素的年龄加到返回的“聚合项”的年龄,
+ //最后的聚合项的年龄就是“总年龄”。
+ //虽然可以使用Sum()直接得到总年龄,但Sum内容也是一样“算法”,只是特例化了。
+ //Aggregate是整个聚合操作的基础,也是最为灵活的一个。
+ next.Age = next.Age + aggregateItem.Age;
+ return next;
+ }
+ );
+
+ var totalAge = agg.Age;
+ var expectedAge = 230 + 28 + 16 + 32;
+
+ Assert.Equal(expectedAge, totalAge);
+ }
+
+ ///
+ /// 重载2:seed 自定初始值和“聚合项”类型
+ ///
+ [Fact]
+ public void Aggregate_seed_func_Test()
+ {
+ List peoples = new List()
+ {
+ new Person(){ Id=1, Name="张三丰", Age=230},
+ new Person(){ Id=2, Name="小龙女", Age=28},
+ new Person(){ Id=3, Name="银花公主", Age=16},
+ new Person(){ Id=4, Name="杨过", Age=32},
+ };
+
+ var seed =0;
+
+ //因为指定了初始聚合项,一共执行了4次“聚合操作”即每一项执行一次“聚合操作”
+ var agg = peoples.Aggregate
+ (
+ seed,
+ (accumulate, currentItem) =>
+ {
+ return accumulate + currentItem.Age;
+ }
+ ) ;
+
+ var totalAge = agg;
+ var expectedAge = 230 + 28 + 16 + 32;
+
+ Assert.Equal(expectedAge, totalAge);
+ }
+
+ ///
+ /// 重载3:seed 自定初始值和“聚合项”类型
+ ///
+ [Fact]
+ public void Aggregate_seed_func_resultSelector_Test()
+ {
+ List peoples = new List()
+ {
+ new Person(){ Id=1, Name="张三丰", Age=230},
+ new Person(){ Id=2, Name="小龙女", Age=28},
+ new Person(){ Id=3, Name="银花公主", Age=16},
+ new Person(){ Id=4, Name="杨过", Age=32},
+ };
+
+ var seed = 0;
+
+ //因为指定了初始聚合项,一共执行了4次“聚合操作”即每一项执行一次“聚合操作”
+ var agg = peoples.Aggregate
+ (
+ //种子项
+ seed,
+
+ //聚合操作
+ (accumulateItem, currentItem) =>
+ {
+ return accumulateItem + currentItem.Age;
+ },
+
+ //改变最后聚合结果,并返回。
+ accumulateItem => "总年龄为:"+ accumulateItem.ToString()
+ );
+
+ var totalAge = agg;
+ var expectedAge = "总年龄为:"+ (230 + 28 + 16 + 32).ToString();
+
+ Assert.Equal(expectedAge.ToString(), totalAge);
+ }
+
+ ///
+ /// InvalidOperationException异常:序列少于1项时。
+ ///
+ [Fact]
+ public void Aggregate_InvalidOperationException_Test()
+ {
+ List peoples = new List();
+
+ Action act =() => peoples.Aggregate
+ (
+ (aggregateItem, next) =>
+ {
+ next.Age = next.Age + aggregateItem.Age;
+ return next;
+ }
+ );
+
+ Assert.Throws(act);
+ }
+ #endregion
+ }
+}
diff --git a/LinqStudy.Test/LinqToObject/GroupTest.cs b/LinqStudy.Test/LinqToObject/GroupTest.cs
index 732400d..2da2993 100644
--- a/LinqStudy.Test/LinqToObject/GroupTest.cs
+++ b/LinqStudy.Test/LinqToObject/GroupTest.cs
@@ -236,7 +236,7 @@ namespace LinqStudy.Test.LinqToObject
.ToList();
var lastItem=group[2].FirstOrDefault();
- var expected="上海松江人";
+ var expected="上海";
Assert.Equal(expected, lastItem);
}