Why does this:
#include <iostream>
#include <string>
#include <vector>
#include <algorithm>
using namespace std;
vector<pair<int, string>> list;
int main() {
int one = 1, two = 2, three =3, five =5, six = 6;
string bla = "bla";
list.push_back( pair<int, string>(two, bla));
list.push_back( pair<int, string>(one, bla));
list.push_back( pair<int, string>(two, bla));
list.push_back( pair<int, string>(six, bla));
list.push_back( pair<int, string>(five, bla));
sort(list.begin(), list.end());
for(auto item : list) {
cout << item.first << endl;
}
}
work as intended? output is:
1
2
2
5
6
How std::sort
gets how to sort my int-string
pairs? How to make it do so for some class of mine as pair first
? Is there a way to sort by second
using std::sort
?
Case 1 : Sorting the vector elements on the basis of first element of pairs in ascending order. This type of sorting can be achieved using simple “ sort() ” function. By default the sort function sorts the vector elements on basis of first element of pairs.
std::sort requires random access iterators and so cannot be used with list .
The std::sort is a sorting function that uses the Introsort algorithm and have the complexity of O(N log(N)) where N= std::distance(first, last) since C++11 and the order of equal elements is not guaranteed to be preserved[3]. The gcc-libstdc++ also uses Introsort algorithm.
std::sort() is a built-in function in C++'s Standard Template Library. The function takes in a beginning iterator, an ending iterator, and (by default) sorts the iterable in ascending order. The function can also be used for custom sorting by passing in a comparator function that returns a boolean.
Since operator<
is defined for std::pair
and it is based on std::pair::first
and then std::pair::second
(lexicographical), so your code is working as the standard. To sort it based on the second part of the std::pair
you can try this:
std::sort(list.begin(), list.end(), [](const std::pair<int, string> &x,
const std::pair<int, string> &y)
{
return x.second < y.second;
});
There is one "obvious" ordering of product types induced by the respective orderings of the components, and that is lexicographical order:
(a, b) < (c, d) <=> a < c || (a == c && b < d)
This is the ordering used by operator<
of std::pair
. In your example, since all the first components are distinct, the ordering happens to be equal to the ordering of the first component. It gets more interesting if you have multiple occurences of the same value in the first component, in which the second component is used to break ties.
How to make it do so for some class of mine as pair first?
You just have to define operator<
for your type. But keep in mind that the second component will be considered if necessary and you might not want that overhead.
Is there a way to sort by
second
usingstd::sort
?
Yes, just use a custom comparator functor. You can always do that if you don't want to use the default operator<
for sorting.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With