std::ranges::views::lazy_split, std::ranges::lazy_split_view
来自 zh.cppreference.net
| 定义于头文件 <ranges>
|
||
template< ranges::input_range V, ranges::forward_range Pattern >
requires ranges::view<V> &&
ranges::view<Pattern> &&
std::indirectly_comparable<ranges::iterator_t<V>,
ranges::iterator_t<Pattern>,
ranges::equal_to> &&
(ranges::forward_range<V> || /*tiny-range*/<Pattern>)
class lazy_split_view
: public ranges::view_interface<lazy_split_view<V, Pattern>>
|
(1) | (C++20 起) |
namespace views {
inline constexpr /* unspecified */ lazy_split = /* unspecified */;
}
|
(2) | (C++20 起) |
| 调用签名 |
||
template< ranges::viewable_range R, class Pattern >
requires /* see below */
constexpr ranges::view auto lazy_split( R&& r, Pattern&& pattern );
|
(C++20 起) | |
template< class Pattern >
constexpr /* range adaptor closure */ lazy_split( Pattern&& pattern );
|
(C++20 起) | |
| 辅助概念 |
||
template< class R >
concept /*tiny-range*/ =
ranges::sized_range<R> &&
requires { /* is-statically-constexpr-sized */<R>; } &&
(std::remove_reference_t<R>::size() <= 1);
|
(3) | (仅用于阐释*) |
1)
lazy_split_view 接受一个 view 和一个分隔符,并将该 view 在分隔符处分割成子范围。
支持两种主要场景:
- 该视图是 input_range,分隔符是单个元素(包装在
single_view中)。 - 该视图是 forward_range,分隔符是一个元素 view。
3) 仅用于阐释的概念
/*tiny-range*/<Pattern> 若满足以下条件则得满足:Pattern 满足 sized_range,Pattern::size() 是常量表达式且适合作为模板非类型实参,并且 Pattern::size() 的值小于或等于 1。值得注意的是,empty_view 和 single_view 满足此概念。lazy_split_view 在底层 view 满足相应概念时满足概念 forward_range 和 input_range V,并且当 同时满足 forward_rangeV 和 common_range 时满足 common_range。
内部范围(ranges::range_reference_t<lazy_split_view>)在底层 view 满足相应概念时满足概念 forward_range 和 input_range V。它不满足 common_range,并且不能与需要 bidirectional_range 或更高要求的算法一起使用。
与 split_view 不同,lazy_split_view 不保持子范围的连续性。
数据成员
| 成员 | 描述 |
V
base_
(private)
|
底层
view
( 仅用于说明的成员对象* ) |
Pattern
pattern_
(private)
|
用作分隔符以分割底层
view
的模式
( 仅用于说明的成员对象* ) |
non-propagating-cache
<
ranges::
iterator_t
<
V
>>
current_
(private)
(仅当
V
不满足
forward_range
时存在)
|
缓存对
begin()
调用结果的对象
( 仅用于说明的成员对象* ) |
成员函数
构造
lazy_split_view
(公开成员函数) |
|
|
返回底层(适配的)视图的副本
(公开成员函数) |
|
|
返回指向起始位置的迭代器
(公开成员函数) |
|
|
返回指向末尾位置的迭代器或哨兵
(公开成员函数) |
|
继承自 ranges::view_interface | |
| 返回派生视图是否为空,仅当它满足 sized_range 或 forward_range 时提供 std::ranges::view_interface<D>的公开成员函数
| |
(C++23) |
返回指向范围起始的常量迭代器 ( std::ranges::view_interface<D>的公开成员函数)
|
(C++23) |
返回范围常量迭代器的哨位 ( std::ranges::view_interface<D>的公开成员函数)
|
| 返回派生视图是否非空,仅当 ranges::empty 可应用于它时提供 ( std::ranges::view_interface<D>的公开成员函数)
| |
| 返回派生视图中的首个元素,当它满足 forward_range 时提供 std::ranges::view_interface<D>(
| |
嵌套类
|
外部迭代器类型
( 仅用于说明的成员类模板* ) |
|
|
内部范围的迭代器类型
( 仅用于说明的成员类模板* ) |
推导指引
注释
名称
lazy_split_view
由后C++20缺陷报告
P2210R2
引入。其惰性机制与修改前的旧版
split_view
保持一致。
示例
运行此代码
#include <algorithm> #include <iostream> #include <ranges> #include <string_view> auto print = [](auto const& view) { // `view` 的类型为 std::views::lazy_split_view::__outer_iterator::value_type for (std::cout << "{ "; const auto element : view) std::cout << element << ' '; std::cout << "} "; }; int main() { constexpr static auto source = {0, 1, 0, 2, 3, 0, 4, 5, 6, 0, 7, 8, 9}; constexpr int delimiter{0}; constexpr std::ranges::lazy_split_view outer_view{source, delimiter}; std::cout << "splits[" << std::ranges::distance(outer_view) << "]: "; for (auto const& inner_view: outer_view) print(inner_view); constexpr std::string_view hello{"Hello C++ 20 !"}; std::cout << "\n" "substrings: "; std::ranges::for_each(hello | std::views::lazy_split(' '), print); constexpr std::string_view text{"Hello-+-C++-+-20-+-!"}; constexpr std::string_view delim{"-+-"}; std::cout << "\n" "substrings: "; std::ranges::for_each(text | std::views::lazy_split(delim), print); }
输出:
splits[5]: { } { 1 } { 2 3 } { 4 5 6 } { 7 8 9 }
substrings: { H e l l o } { C + + } { 2 0 } { ! }
substrings: { H e l l o } { C + + } { 2 0 } { ! }
缺陷报告
下列行为变更缺陷报告被追溯应用于先前发布的 C++ 标准。
| 缺陷报告 | 应用于 | 发布时的行为 | 正确行为 |
|---|---|---|---|
| P2210R2 | C++20 |
旧的
split_view
过于惰性而难以使用
|
将其功能迁移至
lazy_split_view
|
参见
|
(C++20)
|
通过使用分隔符拆分另一个
view
获得的子范围构成的
view
(类模板) (范围适配器对象) |
|
(C++20)
|
由展平
range
s
的
view
所获得的序列构成的
view
(类模板) (范围适配器对象) |