如何使用无参数的函子和具有返回类型的void的函子?

时间:2019-04-03 14:07:02

标签: c++ templates reference

我见过this nice code。并希望将其用于我的情况。

因此,我改变了方向,所以combine(f,g,h)(x)的意思是:做h(g(f(x)))

但实际上我想要:

执行f(x)

如果结果为y,则执行g(y),否则执行g()

如果结果为z,则执行h(z),否则执行h()

所以这是更改后的代码:

template<typename ... Fs>
struct combine_impl
{
    combine_impl(Fs&& ... fs) : functionTuple(std::forward<Fs>(fs) ...) {}
    static constexpr numberOfFs = sizeof ... (Fs);
    template<size_t N, typename ... Ts>
    auto apply(std::integral_constant<size_t, N>, Ts&& ... ts) const
    {
        return apply( std::integral_constant<size_t, N + 1>{}
                    , std::get<N>(functionTuple)(std::forward<Ts>(ts)...));
    }

    template<typename ... Ts>
    auto apply(std::integral_constant<size_t, numberOfFs -1>, Ts&& ... ts) const
    {
        return std::get<numberOfFs -1>(functionTuple)(std::forward<Ts>(ts)...);
    }

    template<typename ... Ts>
    auto operator()(Ts&& ... ts) const
    {
        return apply(std::integral_constant<size_t,0>{}, std::forward<Ts>(ts) ...);
    }

    std::tuple<Fs ...> functionTuple;
};

template<typename ... Fs>
auto combine(Fs&& ... fs)
{
    return combine_impl<Fs ...>(std::forward<Fs>(fs) ...);
}

编辑: 弄清楚问题是什么: 示例:

struct FunctorA
{
   float operator()(int k) const {return k*2.5f;}
};


struct FunctorB
{
   float operator()(float k) const {return k*2.5f;}
};

void main()
{
   float result = combine(FunctorA(),FunctorB())(4);
}

使用该代码可以正常工作。 但我希望也能使用这样的代码:

struct FunctorA
{
   voidoperator()(int k) const 
   {
       // side effects
   }
};


struct FunctorB
{
   float operator()() const 
   {
      return 42.f;
   }
};

void main()
{
   float result = combine(FunctorA(),FunctorB())(4);
}

由于invalid use of void expression,因此无法编译。

编辑: 经过一番阅读:sfinae应该可以做到。 表达式

decltype(std::get<N>(functionTuple)(std::forward<Ts>(std::declval<Ts>())...))

当我需要使用其他版本的apply时,其类型为void。

0 个答案:

没有答案