gpt4 book ai didi

c++ - 为什么 `iota(0) | take(0)` 不是 C++20 中的模型 range::sized_range?

转载 作者:行者123 更新时间:2023-12-03 15:41:08 25 4
gpt4 key购买 nike

考虑以下代码片段:

#include <ranges>

auto r = std::views::iota(0) | std::views::take(0);
static_assert(std::ranges::sized_range<decltype(r)>);
gcc-trunk rejects它用于必需表达式 std::ranges::size(r) 是无效的。为什么 r不是模型 ranges::sized_range ,即,为什么我不能使用 std::ranges::size在上面?
更新
使用后编译 range-v3 . C++23 需要此功能,还是 LWG 问题?
#include <range/v3/all.hpp>
#include <ranges>

auto r = ranges::views::iota(0) | ranges::views::take(0);
static_assert(std::ranges::sized_range<decltype(r)>);
问题似乎是 sentinel_trrange-v3只是 ranges::default_sentinel满足 std::sized_sentinel_for<ranges::counted_iterator> ,因为有一个有效的 operator-[predef.iterators#iterators.counted]对于这两种类型:
friend constexpr iter_difference_t<I> operator-(
const counted_iterator& x, default_sentinel_t);
friend constexpr iter_difference_t<I> operator-(
default_sentinel_t, const counted_iterator& y);

但在 namepace std::ranges , sentinel_trstd::ranges::take_view<std::ranges::iota_view>::_Sentinel<true>不能转换为 std::default_sentinel_t .

最佳答案

views::take only yields a sized range如果给定范围本身的大小。和 views::iota isn't a sized range除非您使用给它一个大小的二元素构造函数之一。你没有。
至于为什么take_view仅在底层迭代器大小时才大小,这是因为 take_view当达到要获取的元素数量或到达基础范围的末尾时停止。这意味着尺寸可能小于您要求的尺寸。所以要计算 take_view 的大小,您必须能够计算基础范围的大小,以查看它是否小于给定的计数。如果您碰巧传递了一个永远不需要计算大小的计数,这并不重要;它是一个编译时属性,而不是基于您在运行时碰巧赋予它的值。
Range V3 如何“工作”尚不得而知,但 C++20 标准不允许它工作。

关于c++ - 为什么 `iota(0) | take(0)` 不是 C++20 中的模型 range::sized_range?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/67068441/

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