std::move_iterator
在标头 <iterator> 定义
|
||
template< class Iter > class move_iterator; |
(C++11 起) | |
std::move_iterator
是一种迭代器适配器,表现与它的底层迭代器(必须至少是一个老式输入迭代器 (LegacyInputIterator) 或实现 input_iterator
(C++20 起))严格相同,但解引用会将底层迭代器返回的值转换为右值。如果此迭代器用作输入迭代器,那么效果是值被移动,而非复制。
嵌套类型
名字 | 定义 | ||||
iterator_type
|
Iter
| ||||
iterator_category (有条件提供) |
| ||||
iterator_concept (C++20 起) |
| ||||
value_type
|
| ||||
difference_type
|
| ||||
pointer
|
Iter
| ||||
reference
|
|
数据成员
名称 | 定义 |
current
|
base() 复制或移动 (C++20 起)的底层迭代器(仅用于阐述的成员对象*) |
成员函数
(C++11) |
构造新的迭代器适配器 (公开成员函数) |
(C++11) |
赋值另一迭代器适配器 (公开成员函数) |
(C++11) |
访问底层迭代器 (公开成员函数) |
(C++11)(C++11)(C++20 中弃用) |
访问被指向的元素 (公开成员函数) |
(C++11) |
按索引访问元素 (公开成员函数) |
推进或回退迭代器 (公开成员函数) |
非成员函数
(C++11)(C++11)(C++20 中移除)(C++11)(C++11)(C++11)(C++11)(C++20) |
比较底层迭代器 (函数模板) |
比较底层迭代器与底层哨位 (函数模板) | |
(C++11) |
令迭代器前进 (函数模板) |
(C++11) |
计算两个迭代器适配器间的距离 (函数模板) |
计算底层迭代器与底层哨位间的距离 (函数模板) | |
(C++20) |
将解引用底层迭代器的结果转换为其关联的右值引用类型 (函数) |
(C++20) |
交换两个底层迭代器所指向的对象 (函数模板) |
(C++11) |
创建拥有从实参推出的类型的 std::move_iterator (函数模板) |
辅助模板
template< class Iterator1, class Iterator2 > requires (!std::sized_sentinel_for<Iterator1, Iterator2>) |
(C++20 起) | |
这个 std::disable_sized_sentinel_for
特化,当底层迭代器不满足 sized_sentinel_for
时,防止 move_iterator
的特化满足这个概念。
注解
功能特性测试宏 | 值 | 标准 | 功能特性 |
---|---|---|---|
__cpp_lib_move_iterator_concept |
202207L | (C++23) | 使 std::move_iterator<T*> 为随机访问迭代器 |
示例
#include <algorithm> #include <iomanip> #include <iostream> #include <iterator> #include <ranges> #include <string> #include <string_view> #include <vector> void print(const std::string_view rem, const auto& v) { std::cout << rem; for (const auto& s : v) std::cout << std::quoted(s) << ' '; std::cout << '\n'; }; int main() { std::vector<std::string> v{"this", "_", "is", "_", "an", "_", "example"}; print("vector 的旧内容:", v); std::string concat; for (auto begin = std::make_move_iterator(v.begin()), end = std::make_move_iterator(v.end()); begin != end; ++begin) { std::string temp{*begin}; // moves the contents of *begin to temp concat += temp; } // 从 C++17 起引入了类模板实参推导,可以直接使用 std::move_iterator 的构造函数: // std::string concat = std::accumulate(std::move_iterator(v.begin()), // std::move_iterator(v.end()), // std::string()); print("vector 的新内容:", v); print("拼接成字符串:", std::ranges::single_view(concat)); }
可能的输出:
vector 的旧内容:"this" "_" "is" "_" "an" "_" "example" vector 的新内容:"" "" "" "" "" "" "" 拼接成字符串:"this_is_an_example"
缺陷报告
下列更改行为的缺陷报告追溯地应用于以前出版的 C++ 标准。
缺陷报告 | 应用于 | 出版时的行为 | 正确行为 |
---|---|---|---|
LWG 2106 | C++11 | 解引用底层迭代器返回纯右值时解引用 move_iterator 会返回悬垂引用
|
改为返回对象 |
LWG 3736 | C++20 | move_iterator 缺失了 disable_sized_sentinel_for 特化
|
已添加 |
P2259R1 | C++20 | std::iterator_traits<Iter>::iterator_category 未定义时也会定义成员 iterator_category
|
不会定义 |
参阅
(C++11) |
创建拥有从实参推出的类型的 std::move_iterator (函数模板) |
(C++20) |
用于 std::move_iterator 的哨位适配器 (类模板) |