Seq.unfold と Seq.zip3 で FizzBuzz

商を求めずに(%を使わないで)FizzBuzzできました。

[<Test>]
let ``fizzbuzz with Seq.unfold and Seq.zip3``() =

let unfold num value = 1 |> Seq.unfold (fun n -> if num = n then Some(Some(value), 1) else Some(None, n + 1))

let nums = seq { for i in 1 .. 100 -> string(i) }
let fizz = unfold 3 "fizz"
let buzz = unfold 5 "buzz"

Seq.zip3 nums fizz buzz
|> Seq.map (function
| (_, Some(f), Some(b)) -> f + b
| (_, Some(f), None ) -> f
| (_, None , Some(b)) -> b
| (n, None , None ) -> n )
|> Seq.iter (printfn "%s")

まず、数値とfizzとbuzzなシーケンスを3つ作っています。fizzとbuzzなシーケンスをunfoldで作っているところがポイント。カウンターでいつfizzやbuzzを格納するのか制御してます。
次に、zip3で3つのシーケンスの要素を組に束ねます。
そして、mapでパターンマッチングを使って出力する文字列を選択し、最後にiterで出力しています。