如何在c++中使用qsort对字符串数组进行排序
How to use qsort to sort array of string in c++?
我在c++中使用qsort对字符串数组进行排序。我的代码如下:
#include <iostream>
#include <cstdlib>
using namespace std;
int CompareString( const void * e1, const void * e2) {
string * s1 = (string * ) e1;
string * s2 = (string * ) e2;
if( *s1 < *s2 ) return -1;
else if( *s1 == *s2 ) return 0;
else if( *s1 > *s2 ) return 1;
}
int main() {
string Array[4] = {"hehe","789","456","123"};
qsort(Array,4,sizeof(string),CompareString);
for( int i = 0;i < 4;++i )
cout << Array[i] << endl;
return 0;
}
但是收到运行时错误。我知道sort在工作,但我想知道为什么我不能使用qsort。谢谢:)
这个问题与这个问题相似但也有一些不同。在这个问题中,人们建议使用sort来代替,或者在琐碎的类型上使用qsort。然而,我的问题是我必须使用qsort而不是sort,所以我的问题在那个问题中没有得到解决,我不认为我的问题是重复的。
至于为什么我必须使用qsort而不是sort,答案是"这是分配的要求",链接是:这里。我把原来的问题翻译如下:
实现MyString类,它继承了std:string,代码应该用下面的代码正确编译和运行:
MyString SArray[4] = {"big","me","about","take"};
qsort(SArray,4,sizeof(MyString), CompareString);
for( int i = 0;i < 4;++i )
cout << SArray[i] << endl;
MyString应该类似于:
class MyString:public string{
...
};
这个原始问题需要MyString通过其他测试,而我已经通过了。但是我还是不能通过qsort,所以我改编了它,问了我的第一个版本的问题。
从答案中,我可以得出结论,qsort不适用于非pod。由于MyString继承了string,而string是非pod的,所以MyString是非pod的,因此MyString不能通过测试。
谢谢大家回答我的问题:)
为了在数组内重新排列和移动c++类,必须使用类的复制/移动构造函数和/或赋值操作符。qsort()
是一个C库函数,它不知道std::string
或任何其他c++类、它的构造函数或析构函数。qsort()
不能用于非pod类的向量排序。
使用std::sort()
来排序你的向量,而不是。
C的qsort
不能移动非pod对象。但是它可以移动指针。因此,如果您必须使用qsort
来对std::string
的数组进行排序,则可以通过对相应的指针数组进行排序来完成:
#include <iostream>
#include <string> // std::string
#include <vector> // std::vector
#include <stdlib.h> // qsort
using namespace std;
auto compare( void const* e1, void const* e2 )
-> int
{
string const* const p1 = *reinterpret_cast<string* const*>( e1 );
string const* const p2 = *reinterpret_cast<string* const*>( e2 );
return p1->compare( *p2 );
}
template< size_t n >
void sort( string (&a)[n] )
{
vector<string const*> pointers;
pointers.reserve( n );
for( string& item : a ){ pointers.push_back( &item ); }
qsort( &pointers[0], n, sizeof( pointers[0] ), compare );
vector<string> result;
result.reserve( n );
for( string const* p : pointers ) { result.push_back( move( *p ) ); }
for( int i = 0; i < int( n ); ++i ) { a[i] = move( result[i] ); }
}
auto main()
-> int
{
string strings[4] = { "hehe", "789", "456", "123" };
sort( strings );
for( string const& s : strings )
{
cout << s << endl;
}
}
string Array[4] = {"hehe","789","456","123"};
产生4个字符串,而不是4个指向string的指针,sizeof(std::string)应该是3*sizeof(void *)+一些常量,如果你的实现是使用SmallStringOptimization。
试着读心术,我猜你认为数组是指向字符串的指针,或者字符串本身是指针。
String最初是这样声明的(如果你删除了所有模板的东西)。
class string {
size_t length;
size_t capacity
char *buffer;
};
如果你已经声明了数组
std::string *Array[4] = {
new std::string("hehe"),
new std::string("789"),
new std::string("456"),
new std::string("123")
};
会成功的。
你可以在这里看到完整的代码
- 将C#字符串数组传递给C++
- 如何为 C 型字符串数组编写 getter 和 setter?
- 有没有办法使用 strcpy 将字符串数组复制到另一个字符串或其他数组中?
- 尝试将 c 字符串数组与分隔符连接起来
- 将字符串数组传递给接受常量字符**的函数
- 返回 C++ 中的字符串数组
- 如何从COM模块中的函数返回字符串数组?
- 无法将字符串数组声明为类成员而不是字符 (C++)
- 删除字符串数组
- 如何将字符串数组返回到 java JNI
- 将字符串数组作为函数参数传递
- C++将字符串数组的元素存储到变量中
- 循环访问还包含未使用元素的字符串数组
- 字符串数组上的 sizeof 运算符以 C++ 为单位给出不同的输出
- 乘以字符串/数组和全局数组
- 递归二进制搜索与字符串数组
- 如何初始化一个标准::字符串数组?
- 无法在声明时使用初始值设定项列表初始化常量字符*/字符串数组的向量
- C++字符串数组的动态向量
- 给定一个等长字符串数组