Edited at

キヨシチェックをC#とReavtiveExtentionsで書いてみた。

More than 3 years have passed since last update.

Rxの勉強で例のキヨシチェックを書いてみた。

他の言語はこんな感じみたいです。

ColdとHotの違いがちょっとだけわかった。

もっとうまく書ける気がする(´・ω・`)

追記:

コメントでBuffer使うと良いってアドバイス貰いました。

使ってみたらけっこう良い感じに書けました。

変更後

using System;

using System.Linq;
using System.Reactive.Concurrency;
using System.Reactive.Linq;

namespace Zundoko
{
internal class Program
{
private const string Zun = "ズン";
private const string Doko = "ドコ";
private const string Kiyoshi = "キ・ヨ・シ! ((└(:3」┌)┘))";

private static void Main(string[] args)
{
var rm = new Random();
Observable
.Interval(TimeSpan.Zero, CurrentThreadScheduler.Instance)
.Select((x, y) => rm.Next()%2 == 0 ? Zun : Doko)
.Do(x => Console.Write($"{x} "))
.Buffer(5, 1)
.Where(x => x.SequenceEqual(new[] {Zun, Zun, Zun, Zun, Doko}))
.Subscribe(x =>
{
Console.WriteLine(Kiyoshi);
Console.Read();
Environment.Exit(0);
});
}
}
}

変更前

using System;

using System.Reactive.Disposables;
using System.Reactive.Linq;
using System.Threading;
using Reactive.Bindings.Extensions;

namespace Zundoko
{
internal class Program
{
private const string Zun = "ズン";
private const string Doko = "ドコ";
private const string Kiyoshi = "キ・ヨ・シ! ((└(:3」┌)┘))";

private static void Main(string[] args)
{
var ms = new ManualResetEventSlim();
var rm = new Random();
var disposable = new CompositeDisposable();

var zundokoRiver = Observable
.Interval(TimeSpan.Zero)
.Select((x, y) => rm.Next()%2 == 0 ? Zun : Doko)
.Publish()
;

zundokoRiver
.Do(x => Console.Write($"{x} "))
.Zip(
zundokoRiver.Skip(1)
, zundokoRiver.Skip(2)
, zundokoRiver.Skip(3)
, zundokoRiver.Skip(4)
, (one, two, three, four, five) => new {one, two, three, four, five})
.Where(x => x.one == Zun && x.two == Zun && x.three == Zun && x.four == Zun && x.five == Doko)
.Subscribe(x =>
{
Console.WriteLine(Kiyoshi);
disposable.Dispose();
ms.Set();
}).AddTo(disposable);

zundokoRiver.Connect();
ms.Reset();
ms.Wait();
Console.Read();
}
}
}