しーしゃーぷで Either クラス書いてた
NuGet 見てみたら、Monad とかいう興味深い単語があったりしたので、書いてみた:
using System; using System.Collections.Generic; using System.Linq; namespace Prelude.Data { /// <summary> /// /// </summary> /// <typeparam name="_Left"></typeparam> /// <typeparam name="_Right"></typeparam> public sealed class Either<_Left, _Right> { /// <summary> /// /// </summary> /// <param name="left"></param> private Either(_Left left) { this.Left = left; } /// <summary> /// /// </summary> /// <param name="right"></param> private Either(_Right right) { this.Right = right; } /// <summary> /// /// </summary> public _Left Left { get; private set; } /// <summary> /// /// </summary> public _Right Right { get; private set; } /// <summary> /// /// </summary> public bool IsLeft { get { return this.which_ == Which.Left; } } /// <summary> /// /// </summary> public bool IsRight { get { return this.which_ == Which.Right; } } /// <summary> /// /// </summary> /// <typeparam name="_A"></typeparam> /// <typeparam name="_B"></typeparam> /// <param name="left"></param> /// <param name="right"></param> /// <returns></returns> public Either<_A, _B> LeftOf<_A, _B>(_A left, _B right = default(_B)) { return new Either<_A, _B>( left ); } /// <summary> /// /// </summary> /// <typeparam name="_A"></typeparam> /// <typeparam name="_B"></typeparam> /// <param name="right"></param> /// <param name="left"></param> /// <returns></returns> public Either<_A, _B> RightOf<_A, _B>(_B right, _A left = default(_A)) { return new Either<_A, _B>( right ); } /// <summary> /// /// </summary> /// <typeparam name="_A"></typeparam> /// <typeparam name="_B"></typeparam> /// <typeparam name="_Result"></typeparam> /// <param name="a"></param> /// <param name="b"></param> /// <param name="value"></param> /// <returns></returns> public static _Result Apply<_A, _B, _Result>(Func<_A, _Result> a, Func<_B, _Result> b, Either<_A, _B> value) { if ( value.IsRight ) { return b( value.Right ); } return a( value.Left ); } /// <summary> /// /// </summary> private Which which_; } }