#ifndef MIGRAPH_GUARD_RTGLIB_FUNCTIONAL_HPP #define MIGRAPH_GUARD_RTGLIB_FUNCTIONAL_HPP #include namespace migraph { struct swallow { template constexpr swallow(Ts&&...) { } }; namespace detail { template struct fix_f { F f; template R operator()(Ts&&... xs) const { return f(*this, std::forward(xs)...); } }; template struct seq { using type = seq; }; template struct merge_seq; template struct merge_seq, seq> : seq { }; template struct gens : merge_seq::type, typename gens::type> { }; template <> struct gens<0> : seq<> { }; template <> struct gens<1> : seq<0> { }; template constexpr void repeat_c_impl(F f, seq) { swallow{(f(std::integral_constant{}), 0)...}; } template constexpr auto sequence_c_impl(F&& f, seq) { return f(std::integral_constant{}...); } } // namespace detail template constexpr void repeat_c(F f) { detail::repeat_c_impl(f, detail::gens{}); } template constexpr auto sequence_c(F&& f) { return detail::sequence_c_impl(f, detail::gens{}); } template constexpr void each_args(F f, Ts&&... xs) { swallow{(f(std::forward(xs)), 0)...}; } template constexpr void each_args(F) { } /// Implements a fix-point combinator template detail::fix_f fix(F f) { return {f}; } template auto fix(F f) { return fix(f); } template auto pack(Ts... xs) { return [=](auto f) { return f(xs...); }; } template auto fold_impl(F&&, T&& x) { return x; } template auto fold_impl(F&& f, T&& x, U&& y, Ts&&... xs) { return fold_impl(f, f(std::forward(x), std::forward(y)), std::forward(xs)...); } template auto fold(F f) { return [=](auto&&... xs) { return fold_impl(f, std::forward(xs)...); }; } } // namespace migraph #endif