首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >同时使用键和值对多映射进行排序

同时使用键和值对多映射进行排序
EN

Stack Overflow用户
提问于 2015-09-26 17:18:29
回答 4查看 12K关注 0票数 1

我试图通过编写一个比较函数来使用标准的排序函数来对其中包含一组对的多映射进行排序,但我在其中遇到了一些错误。我尝试使用值对映射进行排序,然后再次使用键对其进行排序。比较函数导致了一些错误。你能指出我在这方面出了什么问题吗?

代码语言:javascript
复制
#include <iostream>
#include <algorithm>
#include <map>

using namespace std;

bool cmp(const pair<int,int>& a, const pair<int,int>& b)
{
    return a.second < b.second;
}

int main() {
    // multimap of int ssId, int phone numbers
    multimap <int, int> m;
    m.insert(make_pair(1, 8));
    m.insert(make_pair(1, 5));
    m.insert(make_pair(2, 4));
    m.insert(make_pair(2, 3));
    m.insert(make_pair(3, 1));

    sort(m.begin(), m.end(), cmp);
    return 0;
}

输出应如下所示:

代码语言:javascript
复制
1 5
1 8
2 3 
2 4
3 1
EN

回答 4

Stack Overflow用户

发布于 2015-09-26 18:15:53

您正在尝试对严格有序的容器进行排序。这是不可能的,因为在整个multimap中的两个元素的swap通常会违反它的弱排序。例如,使用您提供(想象一下)“排序”的mcmp将是:

3 1

2 3

2 4

1 5

1 8

如您所见,违反了m的顺序。

关联容器不关心值的排序。如果你需要的话,那就点吧

  • 使用另一个有序容器作为值(例如std::map<int, std::set<int>>)
  • std::set<std::pair<int, int>, cmp>与自定义cmp排序一起使用。但请注意,它不是地图:

代码语言:javascript
复制
1. you will not be able to access elements only by `ssId`, but you might access ranges by `lower_bound()` and `upper_bound()`
2. elements of `std::set` are immutable. It means that to change element of `std::set` you have to remove them from set and then insert updated value.

代码语言:javascript
复制
std::set< std::pair<int, int> > m;

m.insert(make_pair(1, 8));
m.insert(make_pair(1, 5));
m.insert(make_pair(2, 4));
m.insert(make_pair(2, 3));
m.insert(make_pair(2, 1));
m.insert(make_pair(2, 5));
m.insert(make_pair(2, 2));
m.insert(make_pair(2, 0));
m.insert(make_pair(3, 1));

for(auto&& x : m) {
    std::cout << x.first << ' ' << x.second << std::endl;
}

auto b = m.lower_bound(std::make_pair(2, 2));
auto e = m.lower_bound(std::make_pair(2, 4));

std::cout << std::endl;

for(auto i = b; i != e; ++i) {
    std::cout << i->first << ' ' << i->second << std::endl;
}

将产生

1 5

1 8

2%0

2 1

2 2

2 3

2 4

2 5

3 1

2 2

2 3

请注意,std::pairstd::tuple都已经有了字典序比较运算符。

票数 2
EN

Stack Overflow用户

发布于 2021-02-06 07:05:02

在C++中没有直接的方法可以做到这一点,因为多重映射是有序的,其顺序不能改变,但是有一个使用额外的多重映射的解决方法。它将精确地输出您喜欢的内容。类似的方法也适用于从字符串到整数的映射,反之亦然。

代码语言:javascript
复制
#include<bits/stdc++.h>
using namespace std;
int main()
{
    multimap <int, int> m;
    m.insert(make_pair(1, 8));
    m.insert(make_pair(1, 5));
    m.insert(make_pair(2, 4));
    m.insert(make_pair(2, 3));
    m.insert(make_pair(3, 1));
    multimap<int, int> R;
    for (auto i=m.begin(); i!=m.end(); i++)
        R.insert({i->second,i->first});
    m.clear();
    for (auto i=R.begin(); i!=R.end(); i++)
        m.insert({i->second,i->first});
    R.clear();
    for (auto i=m.begin(); i!=m.end(); i++)
        cout<<i->first<<"\t"<<i->second<<endl;
    return 0;
}
票数 2
EN

Stack Overflow用户

发布于 2021-02-07 20:47:42

这是一个古老的问题,但如果其他人正在寻找,可能会对他们有用。

对于这种情况,我们希望对同一键的值进行排序,而不是使用

代码语言:javascript
复制
multimap <int, int> m;

使用

代码语言:javascript
复制
map<int,vector<int>> and then sort the individual vector.
or even better, just:
vector<pair<int,int>> and then sort the vector

vector<pair<int, int>> vec{{1,8}, {1,5},{2,4} ,{2,3}, {3,1}};
sort(begin(vec), end(vec));

pair的内部排序将负责按第一个元素进行排序,当第一个元素相同时,它将按第二个元素对这些对进行排序。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/32795546

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档