gpt4 book ai didi

c++ - 带有 C++ lambda 的部分应用程序?

转载 作者:IT老高 更新时间:2023-10-28 22:13:11 29 4
gpt4 key购买 nike

编辑:我在下面使用 curry ,但被告知这是部分应用。

我一直在试图弄清楚如何用 C++ 编写一个 curry 函数,而我真的想通了!

#include <stdio.h>
#include <functional>

template< class Ret, class Arg1, class ...Args >
auto curry( Ret f(Arg1,Args...), Arg1 arg )
-> std::function< Ret(Args...) >
{
return [=]( Args ...args ) { return f( arg, args... ); };
}

我也为 lambdas 编写了一个版本。

template< class Ret, class Arg1, class ...Args >
auto curry( const std::function<Ret(Arg1,Args...)>& f, Arg1 arg )
-> std::function< Ret(Args...) >
{
return [=]( Args ...args ) { return f( arg, args... ); };
}

测试:

int f( int x, int y )
{
return x + y;
}

int main()
{
auto f5 = curry( f, 5 );
auto g2 = curry( std::function<int(int,int)>([](int x, int y){ return x*y; }), 2 );
printf("%d\n",f5(3));
printf("%d\n",g2(3));
}

呸!初始化 g2 的行太大了,我还不如手动 curry 它。

auto g2 = [](int y){ return 2*y; };

要短得多。但是由于意图是拥有一个真正通用且方便的 curry 函数,我可以(1)编写一个更好的函数或(2)我的 lambda 以某种方式隐式构造一个 std::function 吗?当 f 不是自由函数时,我担心当前版本违反了最小意外规则。特别令人讨厌的是我所知道的 make_function 或类似类型的函数似乎不存在。真的,我理想的解决方案只是调用 std::bind,但我不确定如何将它与可变参数模板一起使用。

PS:请不要加分,但如果没有别的,我会解决的。

编辑:我已经知道 std::bind。如果 std::bind 用最好的语法完全符合我的要求,我就不会编写这个函数。这应该更像是一种特殊情况,它只绑定(bind)第一个元素。

正如我所说,我理想的解决方案应该使用绑定(bind),但如果我想使用它,我会使用它。

最佳答案

您的curry函数只是 std::bind 的一个缩小的低效子案例(std::bind1stbind2nd 不应再使用,因为我们有 std::result_of )

你的两行实际上是

auto f5 = std::bind(f, 5, _1);
auto g2 = std::bind(std::multiplies<int>(), 2, _1);

使用 namespace std::placeholders 之后.这小心地避免了装箱到 std::function并允许编译器在调用站点更轻松地内联结果。

对于两个参数的函数,破解类似的东西

auto bind1st(F&& f, T&& t) 
-> decltype(std::bind(std::forward<F>(f), std::forward<T>(t), _1))
{
return std::bind(std::forward<F>(f), std::forward<T>(t), _1)
}

可能有效,但很难推广到可变参数情况(为此,您最终会重写 std::bind 中的大量逻辑)。

柯里化(Currying)也不是部分应用。柯里化(Currying)有“签名”

((a, b) -> c) -> (a -> b -> c)

即。它是将带有两个参数的函数转换为返回函数的函数的操作。它有一个逆uncurry执行反向运算(对于数学家:curryuncurry 是同构,并定义一个附加)。这个逆用 C++ 编写非常麻烦(提示:使用 std::result_of)。

关于c++ - 带有 C++ lambda 的部分应用程序?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/11630379/

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