【问题标题】:Sort vector of objects using TWO criteria使用两个标准对对象的向量进行排序
【发布时间】:2017-03-22 00:15:59
【问题描述】:

假设我有vector<People*> Population

class People {
    string name;
    string city;
    int id;
};

我想先按name排序,然后按city排序,例如:

Anna, Alabama, 1284
Anna, New York, 8377
Daniel, Sydney, 8332
Peter, Alabama, 6392
Peter, Munich, 5590

我想我先按name 排序,然后在name 中按city 排序,然后再转到下一个name

还有更好的方法吗?

【问题讨论】:

  • 你可以一次性排序,只要你使用一个前提条件,同时考虑两个字段。
  • 您为什么使用vector<People*> 而不是vector<People>
  • 如果我理解正确,为了排序,最好有一个指针向量,这样我就不必移动整个对象而只需交换指针。
  • @HichigayaHachiman -- 最好有另一个索引向量,而不是指针,然后交换索引。指针增加了您不需要进入的另一个级别的复杂性。
  • 此外,指针通常会导致内存分散在它来自的任何池中,而不是在一个不错的连续块中,从而剥夺了使vector 在现代处理器上闪电般快速的缓存和预测优势。无论你从使用指针的快速排序中获得什么优势,都会很快被迭代时增加的成本所消耗。类似于链表的情况。

标签: c++ sorting vector


【解决方案1】:

您可以将自定义比较器传递给std::sort

std::sort(Population.begin(), Population.end(), [](People* a, People* b) {
    if (a->name != b->name) return a->name < b->name;
    return a->city < b->city;
});

【讨论】:

  • 该死,你也打败了我吧!
  • 您能解释一下[](People* a, People* b) 的含义吗?我第一次看到这样的东西。
  • [](…) { … }lambda 的语法,又名函数字面量,又名闭包。
【解决方案2】:

您可以利用std::tuple的比较:

std::sort(Population.begin(), Population.end(),
    [](auto& p1, auto& p2) {
        return std::tie(p1->name, p1->city) < std::tie(p2->name, p2->city); 
    });

这样你可以很容易地添加更多的字段进行排序。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-07-08
    • 2021-12-12
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多