问题描述
令我惊讶的是,这个类似概念的断言在 RangeV3 中失败.
To my surprise this Concept-like assertion fails in RangeV3.
#include<vector>
#include<range/v3/algorithm/copy.hpp>
int main(){
static_assert(ranges::WeaklyIncrementable<std::back_insert_iterator<std::vector<double> >>());
}
这是为什么呢?
这意味着我不能像使用 std::copy
那样使用 ranges::copy
算法.
This, among other things means that I cannot use the ranges::copy
algorithm as I use to do with std::copy
.
std::vector<double> w(100);
std::vector<double> v;
ranges::copy(
begin(w), end(w),
std:back_inserter(v)
); // compilation error, concept not fulfilled.
这是在 RangesV3 中 back_insert
的规范方式吗?
Is this the canonical way to back_insert
in RangesV3?
我在 RangeV3 中找不到 WeaklyIncrementable 文档,但在 cppreference https://en.cppreference.com/w/cpp/experimental/ranges/iterator/WeaklyIncrementable 似乎有一个签名的不同类型"可能没有为 back_inserter_iterator
定义.这可能意味着 1 或 3 件事,a) RangeV3 过度约束 copy
要求 b) copy
不是反向插入的算法,c) 我不知道如何使用RangeV3.
I cannot find the WeaklyIncrementable documentation in RangeV3, but in cppreference https://en.cppreference.com/w/cpp/experimental/ranges/iterator/WeaklyIncrementable it seems that there is a "signed different type" that is probably not defined for back_inserter_iterator
. This probably means 1 or 3 things, a) RangeV3 is overconstraining the copy
requirements b) copy
is not the algorithm for back insertion, c) I have no clue how to use RangeV3.
找到这个 https://github.com/ericniebler/range-v3/issues/867,一个可能的解决方法是使用 range::back_inserter(v)
而不是 std::back_inserter(v)
.似乎某处有默认的可构造性要求.
Found this https://github.com/ericniebler/range-v3/issues/867, a possible workaround it to use range::back_inserter(v)
instead of std::back_inserter(v)
. It seems that there is a default constructibility requirement somewhere.
推荐答案
ranges::copy
似乎有一些意想不到的(对我而言)需求.所以 RangesV3 提供了一个替换 ranges::back_inserter
的功能.
It looks like there are some unexpected (to me) requirements need by ranges::copy
. So RangesV3 provides a drop in replacement ranges::back_inserter
that works.
但是,标准中还有许多其他迭代器由于相同的原因不能正常工作,但没有直接替代品,因此可能会变得丑陋.
However there are many other iterators in the standard that do not work for the same reason but to which there is no drop-in replacements, so it can get ugly.
例如,我必须调整一个新的迭代器来替换 std::ostream_iterator
创建一些人工函数,包括一个默认构造函数:
For example, I had to adapt a new iterator to replace std::ostream_iterator
creating some artificial functions, including a default constructor:
template<class T>
struct ranges_ostream_iterator : std::ostream_iterator<T>{
using std::ostream_iterator<T>::ostream_iterator;
ranges_ostream_iterator() : std::ostream_iterator<T>{std::cout}{} // I have to put something here
ranges_ostream_iterator& operator++(){std::ostream_iterator<T>::operator++(); return *this;}
ranges_ostream_iterator& operator++(int){return operator++();}
using difference_type = int;
int operator-(ranges_ostream_iterator const&){return 0;}
};
有了这个,ranges::copy(first,last,ranges_ostream_iterator(std::cout))
工作,而 ranges::copy(first,last,std::ostream_iterator(std::cout))
没有.
With this, ranges::copy(first, last, ranges_ostream_iterator<int>(std::cout))
work, whereas ranges::copy(first, last, std::ostream_iterator<int>(std::cout))
doesn't.
这篇关于为什么在 RangeV3 中 std::back_inserter_iterator 不是 WeaklyIncrementable?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!