Last active
January 3, 2016 23:39
-
-
Save Fuyutsubaki/8536703 to your computer and use it in GitHub Desktop.
ジェネリックラムダ2つを受け取りどちらか1つを返す関数型言語のif式っぽいの
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
//sample http://txt-txt.hateblo.jp/entry/2014/01/21/180633 | |
#include<boost\variant\variant.hpp> | |
#include<type_traits> | |
#include<utility> | |
template<class F1,class F2> | |
class BiGenLambda | |
{ | |
template<class F> | |
using Result_of = typename std::result_of<F>::type; | |
template<class ...Args> | |
using Check_result_of_is_same=typename std::enable_if< | |
std::is_same< | |
Result_of<F1(Args...)>, Result_of<F2(Args...)> | |
>::value | |
>::type; | |
public: | |
BiGenLambda(const F1&f) | |
:data_(f) | |
{} | |
BiGenLambda(const F2&f) | |
:data_(f) | |
{} | |
template<class F,class Result_Type> | |
struct Visitor | |
{ | |
F f_; | |
using result_type = Result_Type; | |
Visitor(const F&f) | |
:f_(f) | |
{} | |
template <class T> | |
result_type operator()(T& x)const | |
{ | |
return f_(x); | |
} | |
template <class T> | |
result_type operator()(const T& x)const | |
{ | |
return f_(x); | |
} | |
}; | |
template<class ...Args, class = Check_result_of_is_same<Args...>> | |
auto operator()(Args&&...args) | |
->Result_of<F1(Args...)> | |
{ | |
auto vi = [&args...](auto c){return c(args...); }; | |
using Vi = decltype(vi); | |
return boost::apply_visitor(Visitor<Vi, Result_of<F1(Args...)>>(vi), data_); | |
} | |
private: | |
boost::variant<F1, F2> data_; | |
}; | |
template<class Than,class Else> | |
BiGenLambda<Than, Else> If(bool r, Than&&than_, Else&&else_) | |
{ | |
if (r)return than_; | |
else return else_; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment