gpt4 book ai didi

c++ - std::vector 的范围 View

转载 作者:行者123 更新时间:2023-12-02 02:33:57 24 4
gpt4 key购买 nike

在提议的 C++20 (The One) Ranges TS 中,将 View 转换为 std::vector 的提议方法是什么?

以下代码无法编译:

int                                           
main() {
std::vector<float> values = {1.0, 2.0, 3.0, 4.0, 5.2, 6.0, 7.0, 8.0, 9.0};
//fmt::print("{}\n", std::experimental::ranges::views::filter(values, [] (float v) { return v < 5.f; }));
std::vector<float> foo = vw::filter(values, [] (float v) { return v < 5.f; });
fmt::print("{}\n", foo);
}

有错误

../src/view.cpp:19:40: error: conversion from     ‘std::experimental::ranges::v1::filter_view<std::experimental::ranges::v1::ref_view<std::vector<float> >, main()::<lambda(float)> >’ to non-scalar type ‘std::vector<float>’ requested
std::vector<float> foo = vw::filter(values, [] (float v) { return v < 5.f; });

(由于某些 CV 限制,注释行也将无法编译)。

那么除了使用基于范围的 for 循环之外,我该如何对 View 执行任何操作呢?

还有一些奖励问题:

  1. 我使用的 cmcSTL2 实现是否符合提案? range-v3 似乎不是。
  2. 有关于 Ranges TS 的任何文档吗?我发现的提案 PDF 几乎是一个 diff 风格的格式非常糟糕的代码转储。事实上,直接阅读 cmcSTL2 源代码对我来说更容易阅读。 cppreference 似乎也缺少......

最佳答案

将 View 转换为 std::vector(或实际上任何其他容器)的 C++20 方法是传递范围的 begin end 成员添加到接受 2 个迭代器(和一个可选分配器)的 vector 构造函数。

我也在寻找这个问题的答案。我真正想要的是接受范围的 std::vector 构造函数的重载。大约:

template <std::ranges::input_range R>
vector(R&& r) : vector(r.begin(), r.end()) {
}

但这不在 C++20 中。

首先,我实现了这个:

namespace rng = std::ranges;

template <rng::range R>
constexpr auto to_vector(R&& r) {
using elem_t = std::decay_t<rng::range_value_t<R>>;
return std::vector<elem_t>{r.begin(), r.end()};
}

它可以工作,但不是很“范围”:https://godbolt.org/z/f2xAcd

然后我做得更好一点:

namespace detail {
// Type acts as a tag to find the correct operator| overload
template <typename C>
struct to_helper {
};

// This actually does the work
template <typename Container, rng::range R>
requires std::convertible_to<rng::range_value_t<R>, typename Container::value_type>
Container operator|(R&& r, to_helper<Container>) {
return Container{r.begin(), r.end()};
}
}

// Couldn't find an concept for container, however a
// container is a range, but not a view.
template <rng::range Container>
requires (!rng::view<Container>)
auto to() {
return detail::to_helper<Container>{};
}

https://godbolt.org/z/G8cEGqeq6

毫无疑问,对于具有 reserve 成员函数的 sized_range 和诸如 std::vector 之类的容器,可以做得更好。

有人提议向 C++23 添加 to 函数 ( https://wg21.link/p1206 ),我确信它会比这做得更好。

关于c++ - std::vector 的范围 View ,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58808030/

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