可変個の集合から、直積の集合を作る(その2)

直積の件でトラバもらった。→ 可変個の集合から、直積の集合を作る - チキン煮込みチーズミックス4辛
自分がPythonよくわからないので、内容は理解できなかったけども><
で、そのトラバをうけて、IEnumerableって無限リスト的に扱えるのかちょっと気になった。
戻り値がIEnumerableのyield returnし続けるメソッドをEnumerateDirectProductに食わせるとどうなるんだろう。
まぁ予想はつくけど、やってみた。

class Program
{
  static void Main(string[] args)
  {
    // 0開始、100開始、200開始の無限リスト(?)を3本
    IEnumerable<IEnumerable<int>> sets =
      new List<IEnumerable<int>>{ EnumerateForEternity(0),
                                  EnumerateForEternity(100),
                                  EnumerateForEternity(200) };
    // 直積を列挙
    var result = EnumerateDirectProduct(sets);
    // とりあえず先頭の100件のみ表示
    var forPrint = result.Select(l => l.Aggregate("{", (acc, n) => acc + " " + n) + "}");
    forPrint.TakeWhile((s, i) => i < 100).ForEach(Console.WriteLine);
  }

  /// <summary>疑似的な無限リスト</summary>
  static public IEnumerable<int> EnumerateForEternity(int start)
  {
    for (int i = start; ; i++) yield return i;
  }

  /// <summary>直積を列挙</summary>
  static public IEnumerable<IEnumerable<T>>
  EnumerateDirectProduct<T>(IEnumerable<IEnumerable<T>> sets)
  {
    return
      sets.Aggregate(
        Enumerable.Repeat(Enumerable.Empty<T>(), 1),
        (prod, list) =>
          from x in prod
          from y in list
          select x.Concat(Enumerable.Repeat(y, 1)));
  }

  static class Extension
  {
    // EnumerableにForEachがないのが理解できん!
    static public void ForEach<T>(this IEnumerable<T> source, Action<T> action)
    {
      foreach (var item in source) action(item);
    }
  }
}

これを実行してみると、

{ 0 100 200}
{ 0 100 201}
{ 0 100 202}
{ 0 100 203}
{ 0 100 204}

  中略

{ 0 100 295}
{ 0 100 296}
{ 0 100 297}
{ 0 100 298}
{ 0 100 299}

となった。当然だけど、3つめの値は無限に続くから、1つ目と2つ目の値はいつまでたっても変わらない。
しかし、EnumerableにForEachが無い理由がわからない。もしかしたらこの前と同様、同じ働きをする違う名前のメソッドがあるのかな...。