boost::optionalは成功か失敗かしかわからないので
失敗した理由付きのoptionalがほしいよね、という話がTwitterでありました。
Maybeモナド(boost::optional)に対するEitherモナドのように
boost::eitherという名前だと仮定して、こんな感じで使えるといいんじゃないかな、と。
either<int> foo(int a) { typedef either<int> result_type; return a >= 0 ? a : result_type("invalid argument", result_type::error_tag()); } either<int> x = foo(-1); if (!x) cout << x.what() << endl; cout << x.get() << endl;
エラーがネストしてた場合なんかは
x.nested().what()
みたいなのも考えたけど空だったときがびみょーなので
ローカルで使える部分特殊化(というか型のパターンマッチ)が言語機能としてほしいなーとか。
(has_nestedみたいなのはあまり書きたくない)
ネストしたエラーのリストとして
for_each(x.nested_errors(), [](either_error e) { cout << e.what() << endl; });
と書ければいいのかな?
あと、エラーを無視させないためにラムダ式を使うとか。
either<int> x(foo(-1), [](either_error e){ cout << e.what() << endl; });
eitherのインタフェースはいろいろ考えないといけないですね。
【参照】
エラー付き戻り値クラステンプレート - にっき(pseudo)
↑throw以外でもエラー内容とりたい。