简体   繁体   中英

sort function does not work properly (c++)

I am trying to sort a vector<pair<string, int>> list , however the sorting seems to not work properly for me.

The vector of pairs contains person's name for a string and years for an integer.

The task is to sort the list by years and if they are same sort by name alphabetically.

The input:

John 20
Tom  25
Mark 20

The output should be :

John 20
Mark 20
Tom  25

My program does not change anything and I cannot find what is wrong. I would appreciate some help.

My code:

vector<pair<string, int>> list;
list.push_back({ "John", 20 });
list.push_back({ "Tom",  25 });
list.push_back({ "Mark", 20 });

sort(list.begin(), list.end(), [](pair<string, int>& a, pair<string, int>& b)
    {
        if (a.second < b.second)
            return a.second > b.second;
        return a.first < b.first;
    }
);

for (const auto& x : list)
    cout << x.first << " " << x.second << endl;

You need your comparison functor to return true if a.second < b.second is true but

if (a.second < b.second)         // if this is `true`
    return a.second > b.second;  // this will always be `false`

A simple approach to correct it is to make a top-down filter like this:

sort(list.begin(), list.end(), [](const auto& a, const b& rhs){ 
    if(a.second < b.second) return true;
    if(b.second < a.second) return false; // note: the operands are flipped

    // if reaching here, a.second and b.second are considered equal (which is
    // not the same as `==` in cases where the operands are floating points)

    return a.first < b.first; // compare the remaining member
});

The above can be made simpler by using std::tie :

sort(list.begin(), list.end(), [](const auto& a, const auto& b){ 
    return std::tie(a.second, a.first) < std::tie(b.second, b.first); 
});

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM