c++ - 您可以从 c++ 中的转换函数使用的函数访问当前迭代器吗?
问题描述
您可以从 c++ 中的转换函数使用的函数访问当前迭代器,以便可以引用之前和之后的值吗?我想使用 transform 函数遍历一个向量,对依赖于当前值之前和之后值的向量执行操作。
例如,假设我有一个值为 [1,2,4,3,5,6] 的向量,我想从第二个值开始,并迭代直到倒数第二个值。在这些元素中的每一个上,我想创建一个新值,该值等于该值的总和,以及原始值中它旁边的值。结束向量看起来像 [7,9,12,14]。
auto originalsBeginIterator = originalPoints.begin();
auto originalsEndIterator = originalPoints.end();
std::advance(originalsBeginIterator, 1);
std::advance(originalsEndIterator,-1);
std::transform(originalsBeginIterator,originalsEndIterator,alteredValues.begin(),
[](int x) x = { return {previous value} + x + {next value};}
);
使用变换时,有什么方法可以引用原始数组中的前一个和后一个值?
解决方案
显然,该工具std::transform
根本没有为您提供执行此操作的方法:它要么将一元谓词应用于一个集合的单个元素,要么将二元谓词应用于两个集合的相应元素。
但关键是,从函数式编程的角度来看,您尝试做的根本不是转换。
你怎么能这样做呢?你可以压缩那个向量,我们称之为v
,同一个向量被剥夺了它的第一个元素,同一个向量被剥夺了它的第二个元素;然后,您将对每对的 3 个元素求和。
Range-v3 为您提供了一种非常简洁的方法:
#include <iostream>
#include <range/v3/view/drop.hpp>
#include <range/v3/view/transform.hpp>
#include <range/v3/view/zip_with.hpp>
#include <vector>
using namespace ranges::views;
int main()
{
// input
std::vector<int> v{1,2,3,4,5,6};
// to sum 3 ints
auto constexpr plus = [](int x, int y, int z){ return x + y + z; };
// one-liner
auto w = zip_with(plus, v, v | drop(1), v | drop(2));
// output
std::cout << w << std::endl;
}
v | drop(1)
给你一个关于元素的观点{2,3,4,5,6}
,以及v | drop(2)
关于{3,4,5,6}
; zip_with
采用n元函数和n范围,并使用 n 元函数组合来自n范围的相应元素的n元组。所以在我们的例子中,它会是这样的:
v = {1, 2, 3, 4, 5, 6}
+ + + +
v1 = v | drop(1) = {2, 3, 4, 5, 6}
+ + + +
v2 = v | drop(2) = {3, 4, 5, 6}
zip_with(plus, v, v1, v2) = {6, 9,12,15}
推荐阅读
- powerbi - 要添加到 Power BI 报表的动态超链接
- python - Python 3.9.7 - if 语句返回 true 时如何继续执行函数?
- mongodb - Spring-data MongoDB 等效查询
- tags - 如何拆分标签和范围以插入/删除标签?
- git - 如何判断哪个 GIT 孩子是新分支?
- javascript - 访问iframe的innerHTML
- vb.net - 用子类更新了一个类,它没有出现在其他类中
- javascript - discord.js SyntaxError:意外的令牌?
- python - tkinter 小部件操作
- python - Django M2M / 1 Django Admin Inline 中与 SELF 的多对多关系