我正在尝试熟悉 C++ 中的 lambda 函数。总的来说,我正在尝试使用 C++ 数字库中的 transform_reduce 函数将一个整数向量转换为一个字符串。经过几个小时的研究,我无法在我的代码中找到错误的来源。这是我的主要 cpp 文件:
#include<vector>
#include<algorithm>
#include<numeric>
#include<iostream>
int main(int argc, const char* argv[])
{
std::vector<int> srcVec = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9};
std::vector<int> destVec;
destVec.resize(srcVec.size());
auto val = std::transform_reduce(srcVec.begin(), srcVec.end(), destVec.begin(),
std::string(), std::plus{},
[](int a){ return std::to_string(a).append(", "); });
std::cout << val.substr(0, val.size() - 2) << std::endl; //print string, remove last comma
return 0;
}
我只将一个参数传递给定义为 transform_reduce() 调用的最后一个参数的匿名函数。我认为 plus 函数也是一个二元运算符类型的函数,可能以某种方式导致了这个“太多参数”错误。然而,我在网上看到过很多与我的用例类似的例子,所以我不认为这是问题所在。
我还阅读了 C++ lambda 的“捕获”语法,想知道修改匿名转换函数的捕获行为是否可以解决我的问题。但是,我理解捕获语法要做的是改变匿名转换函数的返回值是作为浅拷贝还是作为引用传递,所以我没有看到会导致这个问题的方法。
我希望 transform_reduce 函数转换 srcVec 中每个元素的副本,并使用最后一个参数 lambda 函数将其添加到 destVec,然后我希望结合字符串生成的初始值在 destVec 中的每个元素上调用 plus 函数构造函数,通过 plus 函数通过连接将 destVec 减少为字符串。字符串看起来像这样:
0, 1, 2, 3, 4, 5, 7, 8, 9
我认为可能会发生一些并行性问题,但这超出了我的理解范围。
这是一个包含所有错误输出的 pastebin:https://pastebin.com/UqYngUt7
感谢您阅读本文,我们将不胜感激 :)
感兴趣的
std::transform_reduce
有两个版本。看看 cppreference,特别是版本 2 和 3。
版本 2 采用两个范围
Input1
(开始和结束)和 Input2
(仅开始),以及初始累加器值。然后它还需要一个二进制归约操作和一个 binary 转换操作。阅读下面的解释告诉我们原因:
对范围 [first; last) 和从 first2
开始的范围
所以转换被称为:
t(r1[0], r2[0]); t(r1[1], r2[1]); etc.
(至少在概念上,这不是迭代器实际工作的方式)。
这看起来不像你想要的。
另一方面,版本 3 只有一个输入范围,变换操作标记为一元。这看起来更有希望,事实上:
int main()
{
std::vector<int> srcVec = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9};
auto val = std::transform_reduce(srcVec.begin(), srcVec.end(),
std::string(), std::plus{},
[](int a){ return std::to_string(a).append(", "); });
std::cout << val.substr(0, val.size() - 2) << std::endl; //print string, remove last comma
}
编译并生成:
0, 1, 2, 3, 4, 5, 6, 7, 8, 9