gpt4 book ai didi

c++ - 如何将函数的 y→λx.yx 'lifting' 执行到仿函数中?

转载 作者:搜寻专家 更新时间:2023-10-31 00:31:04 24 4
gpt4 key购买 nike

编辑:单行摘要:是否可以创建一个模板化类型,其 operator() 调用任意函数,指定为模板参数?


考虑(模板化的)函数

template <typename T> std::operator-(const T& lhs, const T& rhs)

在标准 C++ 库中,在 <functional> 中我们 have以下构造(忽略 constexpr 和 C++14 中的默认 void,以及 binary_function 的便利继承):

  template<typename T>
struct minus {
T operator()(const T& lhs, const T& rhs) const {
return operator-(lhs, rhs)
};
};

因此,“仿函数”(标准库用语)std::minus是函数 operator- 的一种“提升” .我们同样有std::plus , std::multiplies等等。

现在,假设我想为任意函数实现同样的效果。这是我如何使用宏来实现的(对于已知数量的参数,比如 2)

#define CONCAT(s1,s2) s1##s2
#define EXPAND_THEN_CONCAT(s1,s2) CONCAT(s1,s2)
#define DEFINE_FUNCTOR(f, ret_type, param1_type, param2_type) \
struct EXPAND_THEN_CONCAT(f,_functor) { \
ret_type operator()(param1_type x, param2_type y) const { \
return f(x, y) \
}; \
};

...但是我当然想用 C++11 的方式(如果有帮助的话,也可以用 C++14 的方式)。我该怎么做?

我想以某种方式将 f 作为模板参数传入;但是如何使 operator() 具有与 f 相同的签名(并带有 const 标记)?对于一个固定的签名,我认为它不会那么困难,代码应该像std::minus。 - 但总的来说,我真的看不出它是如何完成的。

我曾想过尝试一些类似于我在函数的“提升调用”中使用的东西:

template<typename F, typename... Parameters>
inline void invoke(const F& f, Parameters... parameters) {
f(parameters...);
}

但是,同样,这不会削减它 - 这会让我得到我喜欢的执行,但不是我喜欢的签名;我需要那个签名...

最佳答案

std::minus 是一个类型。它是一种具有 operator() 重载的类型,恰好在给定的参数上调用 operator-

你是在问是否有办法创建一个可以调用任意函数的类型?这将需要您以某种方式指定调用该类型的函数。为类型提供参数的唯一方法是通过模板参数。

同时 non-type template parameters可能是函数指针,它们不会像 std::minus 那样工作,它通过重载解析等调用 operator-。函数指针指向特定函数,而不是重载集。

您似乎想要的是能够指定一个标识符,并取回一个对象,该对象在被调用时将调用该标识符,就像您直接调用它一样。这包括重载决议等。

C++ 作为一种语言无法做到这一点。论文P0119 (PDF)是添加此类语言功能的提案,尽管它不处理成员函数。目前尚不清楚它在 2015 年在科纳的去向,甚至是否出现过。

您可以获得的最接近的是通过 C++14 lambdas 对您的宏进行细化:

#define CREATE_FUNCTOR(f) \
[=](auto&& ...args) -> decltype(auto) \
{ \
return f(std::forward<decltype(args)>(args)...); \
}

这里使用 lambda 的原因是,如果你在成员函数中使用 this,如果 f 恰好是一个,lambda 将能够捕获 this成员函数。它也将被视为封闭类型的友元。

当然,这会创建一个值,而不是类型。

关于c++ - 如何将函数的 y→λx.yx 'lifting' 执行到仿函数中?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34981563/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com