22

I am trying to sort an array of strings, but it's not sorting anything.... what am I doing wrong?

string namesS[MAX_NAMES];

int compare (const void * a, const void * b){
    return ( *(char*)a - *(char*)b );
}


void sortNames(){

    qsort(namesS, MAX_NAMES, sizeof(string), compare);
}
3
  • 1
    Are you considering only the first letter of the strings? Commented May 10, 2010 at 13:52
  • 11
    "what am I doing wrong?" Using qsort, treating string as a char *... Commented May 10, 2010 at 13:53
  • 1
    Your compare function tries to cast a string to a char *. That's definitely not a sane thing to do. Commented Dec 29, 2012 at 4:49

6 Answers 6

49

This is C++, not C. Sorting an array of strings is easy.

#include <string>
#include <vector>
#include <algorithm>

std::vector<std::string> stringarray;
std::sort(stringarray.begin(), stringarray.end());
Sign up to request clarification or add additional context in comments.

5 Comments

Note that you can use std::sort on an array too (but std::vector is a better idea): std::sort(namesS, namesS+MAX_NAMES);
This is convenient but will not handle case sensitivity. Uppercase W will come before Lowercase a.
If you want case sensitivity, you need a serious Unicode algorithm and library.
Not exactly, you can pass a custom compare function or functor to std::sort and do a case-insensitive comparison there.
Only if you have a proper Unicode case-insensitive comparison.
10

std::qsort is inherited from the standard C library. It will not work.

You need to use std::sort for sorting strings.

Specifically, cast std::string to void* and then to char* is undefined and won't work.

2 Comments

" It will not work." It can be made to work. That's not to say it should be made to work.
@JohnDibling: qsort only works with blitable (trivially copyable) types, which std::string is not.
8

algorithm sort in CPP has the same complexity as qsort:

#include <iostream>
#include <algorithm>
#include <vector>
#include <string>
using namespace std;

bool compare(string a, string b){
    cout << "compare(" << a << "," << b << ")" << endl;
    return (a.compare(b) < 0);
}

int main () {

    string mystrs[] = {"www","ggg","bbb","ssss","aaa"};
    vector<string> myvector (mystrs, mystrs + 5);               
    vector<string>::iterator it;

  sort (myvector.begin(), myvector.end(), compare);

  cout << "vector contains:";
  for (it=myvector.begin(); it!=myvector.end(); ++it)
    cout << " " << *it;

  cout << endl;

  return 0;
}

1 Comment

This contained an example initialization of vector<string>, not just an example declaration! Thank you, better than accepted answer!
1

You can use boost::sort, like this:

#include <vector>
#include <boost/range/algorithm.hpp>

std::vector<std::string> stringarray;
boost::sort(stringarray);

If you want use find use boost::find, like this:

std::string findme;
auto offset = boost::find(stringarray, findme) - stringarray.begin()

See 2 useful functions (m_stringarray should be member of ClassA):

const size_t ClassA::GetIdByName(std::string name) const
{
    return (boost::find(this->m_stringarray, name) - this->m_stringarray.begin());
}

const std::string ClassA::GetNameById(size_t id) const
{
    return this->m_stringarray[id];
}

Comments

1

As many here have stated, you could use std::sort to sort, but what is going to happen when you, for instance, want to sort from z-a? This code may be useful

bool cmp(string a, string b)
{
if(a.compare(b) > 0)
    return true;
else
    return false;
}

int main()
{
string words[] = {"this", "a", "test", "is"};
int length = sizeof(words) / sizeof(string);
sort(words, words + length, cmp);

for(int i = 0; i < length; i++)
    cout << words[i] << " ";
cout << endl;
    // output will be: this test is a 

}

If you want to reverse the order of sorting just modify the sign in the cmp function.

1 Comment

The body of cmp can be just return a < b;, which is also easy to reverse. One can also avoid implementing a custom cmp and just pass either std::less<std::string>() or std::greater<std::string>() to std::sort
0

Here is C++ another way to sort array of string without using <vector>.

#include <iostream>
#include <algorithm>

using namespace std;

int main() {
    string WordArray[] = {"AA","DD","CC","BB","ZZ","NN"};
    sort(begin(WordArray), end(WordArray));  /*Sort the Array*/
    for(auto& Word: WordArray){
       cout<<Word<<endl;                     /*Print Every String Element*/
    }
    return 0;
}

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.