Reputation: 119
Is there any way in C++, That will sort me a pairs of vector based on the difference of the pair values. As an example, Suppose I have 4 pairs
1 3,
5 6,
2 3,
12 5,
so, the differences of the pairs are 2 1 1 7, if I sort in descending order The sorted vector would be,
12 5,
1 3,
5 6,
2 3,
I hope you understood what my problem is. Is there any way to sort the elements this way?
I have tried this way to sort elements based on first or second element. But this is not my problem. My problem is I need sort that based on the difference.
bool sortinrev(const pair<int,int> &a, const pair<int,int> &b){
return(a.first > b.first) ;
}
int main()
{
vector< pair <int,int> > pq;
for(int i=1; i<=4; i++){
int x,y;
cin >> x >> y;
pq.push_back(make_pair(x,y));
}
sort(pq.begin(), pq.end(), sortinrev);
for(int i=0; i<4; i++){
cout << pq[i].first << " " << pq[i].second << endl;
}
return 0;
}
Upvotes: 4
Views: 2585
Reputation: 35154
The standard library provides a data structure std::pair
and a sorting algorithm std::sort
, to which you can pass your custom comparison that defines the order. See the following code, that defines a comparator taking two std::pair<int,int>
and comparing them based on their "absolute difference", together with the code how to invoke std::sort
with it. Hope it helps.
#include <iostream>
#include <vector>
int main()
{
std::vector<std::pair<int,int> > v = {
{1, 3},
{5, 6},
{2, 3},
{12, 5}
};
// sort using a custom function object
struct {
bool operator()(const std::pair<int,int> &a, const std::pair<int,int> &b) const
{
return ( abs(a.first-a.second) > abs(b.first-b.second));
}
} differenceIsGreater;
std::sort(v.begin(), v.end(), differenceIsGreater);
for (auto a : v) {
std::cout << "(" << a.first << "," << a.second << ")" << std::endl;
}
return 0;
}
Output:
(12,5)
(1,3)
(5,6)
(2,3)
Upvotes: 2
Reputation: 91
std::sort has an overload that takes a compare callable.
template< class RandomIt, class Compare >
void sort( RandomIt first, RandomIt last, Compare comp );
So, you can pass a lambda (or other function) as that third parameter that tcompares any way that you want.
From cppreference.com:
comp - comparison function object (i.e. an object that satisfies the requirements of Compare) which returns true if the first argument is less than (i.e. is ordered before) the second.
The signature of the comparison function should be equivalent to the following:
bool cmp(const Type1 &a, const Type2 &b);
The signature does not need to have const &, but the function object must not modify the objects passed to it.
The types Type1 and Type2 must be such that an object of type RandomIt can be dereferenced and then implicitly converted to both of them.
So, for example
sort(begin(myvect), end(myvect), [](auto p) { /* comparison code */ });
(that requires c++14, you may have to modify that depending on your compiler version)
Upvotes: 1
Reputation: 117856
If your container is
std::vector<std::pair<int, int>> data;
you could sort it as
std::sort(std::begin(data),
std::end(data),
[](std::pair<int, int> const& lhs, std::pair<int, int> const& rhs)
{
return std::abs(lhs.first - lhs.second) < std::abs(rhs.first - rhs.second);
});
If you want to switch between ascending and descending just switch from <
to >
accordingly.
Upvotes: 8