重载运算符<对不被用于排序

时间:2015-09-16 08:53:24

标签: c++ sorting

我重载了pair<int,int>的少于操作,因此我可以按特定方式对矢量进行排序。我希望它按照一对中的第一个键按升序排列,如果第一个键相等,那么我根据第二个键按降序排列。

问题是sort函数似乎没有使用重载的<运算符,但是如果在2对上调用<,则返回的输出就是我所期望的。我附上了一段代码,我将用于测试:

#include <iostream>
#include <vector>
#include <algorithm>

using namespace std;
bool operator<(pair<int, int> &a, pair<int, int> &b)
{
    if (a.first < b.first) return true;
    else if ((a.first == b.first) && (a.second > b.second)) return true;
    return false;
}

int main() {
    vector<pair<int, int>> test {make_pair(1,10), make_pair(3,4), make_pair(3,8),  make_pair(6, 23), make_pair(1,6)};
    sort(test.begin(), test.end());
    for (int i = 0; i < test.size(); i++)
      cout << test[i].first << " - " << test[i].second << "  ";
    cout << endl;
    auto a = make_pair(3,4);
    auto b = make_pair(3,8);
    cout << (a < b) << endl;
    return 0;
}

输入向量为{(1,10), (3,4), (3,8), (6,23), (1,6)}

我希望输出为{(1,10), (1,6), (3,8), (3,4), (6,23)}

获得的输出为{(1,6), (1,10), (3,4), (3,8), (6, 23)}

如您所见,获得的输出是您使用标准<运算符而不会重载的结果。所以我认为这可能是一个问题,并检查(3,4) < (3,8)。在这种情况下,根据我的重载运算符,答案返回false。那我哪里错了?为什么#{1}}不会受到重载运营商的影响?有关类似问题的SO有各种各样的问题,但无法找到任何有帮助的问题。

2 个答案:

答案 0 :(得分:11)

已经为operator<命名空间中的对定义了std,这是std::sort版本找到的那个对struct MyPairComparator { bool operator()(const std::pair<int, int> & a, const std::pair<int, int> & b) const { // ... } }; sort(test.begin(), test.end(), MyPairComparator()); // ADL, maybe // ^^^^^^^^^^^^^^^^^^ 你正在使用。从未发现过载。改为使用命名谓词:

sort

此外,谓词应该可以用常量值调用,所以要么通过值或const引用来获取参数。

请注意,std位于<命名空间中。相比之下,当您在main中使用/:name表达式时,确实找到了您自己在全局命名空间中的重载。

答案 1 :(得分:1)

您似乎使用C ++ 11编译器,使用lambda函数更正并使其更容易。像

这样的东西
sort(test.begin(), test.end(), [](const pair<int, int> & a, const pair<int, int> & b) {
    if (a.first < b.first) return true;
    else if ((a.first == b.first) && (a.second > b.second)) return true;
    return false;
});