diff --git a/include/utempl/utils.hpp b/include/utempl/utils.hpp index da223e1..436e878 100644 --- a/include/utempl/utils.hpp +++ b/include/utempl/utils.hpp @@ -221,4 +221,31 @@ inline constexpr auto Filter(Tuple&& tuple, auto&& f) { ); }; +template +struct Curryer { + F f; + Tuple data; + inline constexpr operator decltype(f(std::declval()...))() && { + return [&](std::index_sequence){ + return this->f(std::move(Get(this->data))...); + }(std::index_sequence_for()); + }; + inline constexpr operator decltype(f(std::declval()...))() const { + return [&](std::index_sequence){ + return this->f(Get(this->data)...); + }(std::index_sequence_for()); + }; + template + inline constexpr auto operator()(T&& arg) const -> Curryer>{ + return {.f = this->f, .data = this->data + Tuple{std::forward(arg)}}; + }; +}; +template +inline constexpr auto Curry(F&& f) -> Curryer> { + return {.f = std::forward(f), .data = Tuple{}}; +}; + +static_assert(Curry([](auto... args) {return (0 + ... + args);})(1)(2)(3) == 6); + + } // namespace utempl