[英]Unqualified sort() -- why does it compile when used on std::vector and not on std::array, and which compiler is correct?
When calling std::sort()
on a std::array
:在std::array
上调用std::sort()
时:
#include <vector>
#include <array>
#include <algorithm>
int main() {
std::vector<int> foo{4, 1, 2, 3};
sort(begin(foo), end(foo));
std::array<int, 4> foo2{4, 1, 2, 3};
sort(begin(foo2), end(foo2));
}
Both gcc and clang return an error on the sort on the std::array
-- clang says gcc 和 clang 都在std::array
上的排序上返回错误——clang 说
error: use of undeclared identifier 'sort';错误:使用未声明的标识符“排序”; did you mean 'std::sort'?你的意思是'标准::排序'?
Changing to std::sort(begin(foo2), end(foo2))
fixes the problem.更改为std::sort(begin(foo2), end(foo2))
解决问题。
MSVC compiles the code above as written. MSVC 按照编写的方式编译上面的代码。
Why the difference in treatment between std::vector
and std::array
;为什么std::vector
和std::array
之间的处理不同; and which compiler is correct?哪个编译器是正确的?
This is comes down to the type that begin
and end
result to and how that works with Argument Dependent Lookup .这归结为begin
和end
结果的类型以及它如何与Argument Dependent Lookup 一起使用。
In在
sort(begin(foo), end(foo));
you get你得到
sort(std::vector<int>::iterator, std::vector<int>::iterator)
and since std::vector<int>::iterator
is a member of std
ADL finds sort
in std
and the call succeeds.并且由于std::vector<int>::iterator
是std
ADL 的成员,因此在std
找到sort
并且调用成功。
With和
sort(begin(foo2), end(foo2));
You get你得到
sort(int*, int*)
and because int*
is not a member of std
, ADL will not look into std
and you can't find std::sort
.并且因为int*
不是std
的成员,ADL 不会查看std
并且您找不到std::sort
。
This works in MSVC because这在 MSVC 中有效,因为
sort(begin(foo2), end(foo2));
becomes变成
sort(std::_Array_iterator, std::_Array_iterator)
and since std::_Array_iterator
is part of std
ADL finds sort
.并且由于std::_Array_iterator
是std
ADL 的一部分std::_Array_iterator
sort
。
Both compilers are correct with this behavior.两个编译器都对这种行为是正确的。 std::vector
and std::array
don't have any requirement on what type is used for the iterator except that it satisfies the LegacyRandomAccessIterator requirement and in C++ 17 for std::array
that the type also be a LiteralType and in C++20 that it be a ConstexprIterator std::vector
和std::array
对迭代器使用的类型没有任何要求,只是它满足LegacyRandomAccessIterator要求,并且在 C++17 中对于std::array
类型也是LiteralType和 C+ +20 它是ConstexprIterator
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.