LINQでお馴染み?Aggregateみたいな動きをするメソッドも当然Reactive Extensionsで使えます!!
ただ、Aggregateは集計し終わった値だけ返しますが、集計途中の値を全て報告してくれるScanというメソッドもあります。
使い方は、どちらも同じで第一引数に初期値、第二引数に集計中の値、戻り値に現在の集計結果を返すというものです。動きの違いを見るにはサンプルプログラムを動かしてみるのが一番です。ということで早速やってみます。
var ob = Observable.Range(1, 20); Console.WriteLine("Scan"); ob.Scan(string.Empty, (s, i) => { if (i % 15 == 0) return s + "FizzBuzz"; if (i % 3 == 0) return s + "Fizz"; if (i % 5 == 0) return s + "Buzz"; return s + i.ToString(); }).Subscribe(Console.WriteLine); Console.WriteLine("Aggregate"); ob.Aggregate(string.Empty, (s, i) => { if (i % 15 == 0) return s + "FizzBuzz"; if (i % 3 == 0) return s + "Fizz"; if (i % 5 == 0) return s + "Buzz"; return s + i.ToString(); }).Subscribe(Console.WriteLine);
実行結果は以下のようになります。
Scan 1 12 12Fizz 12Fizz4 12Fizz4Buzz 12Fizz4BuzzFizz 12Fizz4BuzzFizz7 12Fizz4BuzzFizz78 12Fizz4BuzzFizz78Fizz 12Fizz4BuzzFizz78FizzBuzz 12Fizz4BuzzFizz78FizzBuzz11 12Fizz4BuzzFizz78FizzBuzz11Fizz 12Fizz4BuzzFizz78FizzBuzz11Fizz13 12Fizz4BuzzFizz78FizzBuzz11Fizz1314 12Fizz4BuzzFizz78FizzBuzz11Fizz1314FizzBuzz 12Fizz4BuzzFizz78FizzBuzz11Fizz1314FizzBuzz16 12Fizz4BuzzFizz78FizzBuzz11Fizz1314FizzBuzz1617 12Fizz4BuzzFizz78FizzBuzz11Fizz1314FizzBuzz1617Fizz 12Fizz4BuzzFizz78FizzBuzz11Fizz1314FizzBuzz1617Fizz19 12Fizz4BuzzFizz78FizzBuzz11Fizz1314FizzBuzz1617Fizz19Buzz Aggregate 12Fizz4BuzzFizz78FizzBuzz11Fizz1314FizzBuzz1617Fizz19Buzz
Scanが集計中の値をSubscribeしたものに通知してるのに比べてAggregateは集計結果だけSubscribeしたものに通知してるのがわかります。