c++ - c ++ - 我可以在堆分配的原始数组上使用std :: sort吗?

我们知道当使用连续内存块时,很容易得到迭代器(这里是&arra[0]arra )并将迭代器传递给std::sort 。

举个例子:


int arra[100];


 for (int i = 0; i < 100; i++) {


 arra[i] = rand() % 32000;


 }


 for (int i = 0; i < len; i++)std::cout << arra[i]<<"";


 std::sort(arra,arra+100);



现在,如果分配了一个堆数组,就像这里的arr一样:


int len;


 len = 100;


 int* arr = new int[len];


 for (int i = 0; i < len; i++) {


 arr[i] = rand() % 32000;


 }



我不知道是否可以为此数组获取迭代器,所以,我可以在这个数组中使用std::sort ,如果没有,在这样的数组中使用std::sort有什么解决方法?

时间:

指针符合RandomAccessIterator所要求的标准,这是std::sort ,只要指向堆栈内存或堆内存,只要指向同一个(连续)数组,它们就不重要了,因此,你可以简单地使用:


std::sort(arr, arr + len);



也就是说,std::vector可能是在堆上分配数组的更好选择,它为你节省管理内存的麻烦。

可以,在两种情况下都可以使用std::sortstd::sort不知道或关心内存分配的方式。

在C 库中迭代器基本上是Fancy指针,因此,它是标准符合仅增加指针到数组末尾以获得"结尾"指针的标准:


#include<algorithm>


#include<iostream>



int main() {


 int len;


 len = 100;


 int* arr = new int[len];


 for (int i = 0; i < len; i++) {


 arr[i] = rand() % 32000;


 }


 //Valid, Defined Behavior that works as expected


 std::sort(arr, arr + len);


 //alternative, to make the code easier to read:


 //auto begin = arr;


 //auto end = arr + len;


 //std::sort(begin, end);


 for(int i = 0; i < len; i++)


 std::cout << arr[i] << std::endl;


}



但是,一些编译器(像可视化编译器)认识到这种代码本质上是不安全的,因为需要手动提供数组长度,因此,如果您尝试执行此操作,它们将导致(可以使用Compiler标志进行压缩)编译时错误,并建议您使用编译器提供的实用程序:


#include<algorithm>


#include<iostream>



int main() {


 int len;


 len = 100;


 int* arr = new int[len];


 for (int i = 0; i < len; i++) {


 arr[i] = rand() % 32000;


 }



 //MSVC Specific Code!


 auto begin = stdext::make_checked_array_iterator(arr, len);


 auto end = arr + len;


 std::sort(begin, end);


 for(int i = 0; i < len; i++)


 std::cout << arr[i] << std::endl;


}



有关Visual Studio编译器的更多信息,请参见这里: https://docs.microsoft.com/en-us/cpp/standard-library/checked-iterators?view=vs-2019

...