2020-08-15

 

转自csdn的文章,仅作为学习笔记。原文链接:https://blog.csdn.net/qq_30603195/article/details/86660263

文章目录

 

map没有随机迭代器,只有顺序迭代器,所以不能用sort

  1. map按键值Key排序

  • 默认按照less<key>升序排列
    #include<iostream>
    #include<map>
    using namespace std;
    int main()
    {
        srand((unsigned)time(NULL));
        multimap<int,int>mp;
    // multimap第三个参数默认为less<Key>,即 less<int>
        int n;
        cin>>n;
        int a,b;
        for(int i=0; i<n; i++)
        {
            a=rand()%4;
            b=rand()%4;
            //插入
            mp.insert(pair<int,int>(a,b));
        }
        map<int,int>::iterator iter;
        //遍历输出
        for(iter=mp.begin(); iter!=mp.end(); iter++)
            cout<<iter->first<<" "<<iter->second<<endl;
        return 0;
    }
    

    输入8,Key升序,Value随机:
    1 1
    1 1
    1 2
    2 1
    3 3
    3 0
    3 3
    3 2

  • 定义map时,用greater< Key>实现按Key值递减插入数据

  • multimap<int,int,greater<int> >mp;
    //注意<int>后空一格
    

    输入8,Key值降序排列,Value随机:
    3 0
    3 3
    3 1
    2 3
    2 0
    1 0
    0 0
    0 0

  • 当Key值为自定义的类时

  • 写一个函数对象1(仿函数)

  • #include<iostream>
    #include<map>
    using namespace std;
    typedef struct tagIntPlus
    {
        int num,i;
    }IntPlus;
    //自定义比较规则
    //注意operator是(),不是<
    struct Cmp
    {
        bool operator () (IntPlus const &a,IntPlus const &b)const
        {
            if(a.num!=b.num)
                return a.num<b.num;
            else return a.i<b.i;
        }
    };
    int main()
    {
        srand((unsigned)time(NULL));
        //注意此处一定要有Cmp,否则无法排序会报错
        multimap<IntPlus,int,Cmp>mp;
        int n;
        cin>>n;
        int a,b;
        IntPlus intplus;
        for(int i=0; i<n; i++)
        {
            a=rand()%4;
            b=rand()%4;
            intplus.num=a;
            intplus.i=b;
            mp.insert(pair<IntPlus,int>(intplus,i));
        }
        map<IntPlus,int>::iterator iter;
        for(iter=mp.begin(); iter!=mp.end(); iter++)
            cout<<iter->first.num<<" "<<iter->first.i<<" "<<iter->second<<endl;
        return 0;
    }
    

    输入8,
    结果按Key值的num升序排列,当num值相等时按Key值的i升序排列
    当Key值相等时按插入顺序排列
    此时虽然表现为按Value值升序排列,但实际上只是插入的顺序巧合而已

  • Key.numKey.ii【Value】
    030
    112
    116
    217
    221
    305
    313
    334
  • 在类里重载小于号<
    注意只重载小于号,不要去重载大于号
    如果想改变为 升 / 降序列,只需改变判断条件即可
  • typedef struct tagIntPlus
    {
        int num,i;
        bool operator < (tagIntPlus const& intplus)const
        {
            //当num不等时
            //前一个对象的num>后一个时返回true,降序排列。
            //反之升序排列
            if(num!=intplus.num)
                return num>intplus.num;
            //当num相等时
            //前一个对象的i<后一个时返回true,升序排列
            else return i<intplus.i;
        }
    }IntPlus;
    
    主函数只需将第一种方法中的map中的Cmp去掉即可
  • multimap<IntPlus,int>mp;
    

    输入8,结果:

  •  

    Key.numKey.ii【Value】
    020
    011
    015
    002
    224
    333
    326
    317
  • map按值Value排序

  • 再次强调不能用sort
    只能将map中数据压入能用sort的容器,如vector

  • #include<iostream>
    #include<map>
    #include<vector>
    #include<algorithm>//sort
    using namespace std;
    
    typedef struct tagIntPlus
    {
        int num,i;
    } IntPlus;
    
    typedef pair<tagIntPlus,int> PAIR;
    

    必须有Cmp。
    虽然之后会sort,map的排序并不重要,
    但是map输入数据时需要比较Key值,没有会报错

  • struct Cmp
    {
        bool operator () (IntPlus const &a,IntPlus const &b)const
        {
            if(a.num!=b.num)
                return a.num<b.num;
            else return a.i<b.i;
        }
    };
    

    map会按键值Key升序排列,Value值无要求

  • 下面才是重点:

  • bool cmp(PAIR const&a,PAIR const&b)
    {
        if(a.first.num!=b.first.num)
            return a.first.num<b.first.num;
        else
        {
            if(a.first.i!=b.first.i)
                return a.first.i<b.first.i;
            else return a.second>b.second;
        }
    }
    
    int main()
    {
        srand((unsigned)time(NULL));
        multimap<IntPlus,int,Cmp>mp;
        int n;
        cin>>n;
        int a,b;
        IntPlus intplus;
        for(int i=0; i<n; i++)
        {
            a=rand()%4;
            b=rand()%4;
            intplus.num=a;
            intplus.i=b;
            mp.insert(pair<IntPlus,int>(intplus,i));
        }
        map<IntPlus,int>::iterator iter;
        cout<<"排序前:"<<endl;
        for(iter=mp.begin(); iter!=mp.end(); iter++)
            cout<<iter->first.num<<"|"<<iter->first.i<<"|"<<iter->second<<endl;
    
        cout<<"排序后:"<<endl;
        vector<PAIR>vec(mp.begin(),mp.end());
        sort(vec.begin(),vec.end(),cmp);
        int size=vec.size();
        for(int i=0;i<size;i++)
            cout<<vec[i].first.num<<"|"<<vec[i].first.i<<"|"<<vec[i].second<<endl;
        return 0;
    }
    
    

    输入8:

  • 排序前:

  • Key.numKey.ii【Value】
    000
    005
    012
    017
    023
    134
    201
    336

    排序后:

    key肯定都没变,Vaule 如愿降序!

    Key.numKey.ii【Value】
    005
    000
    017
    012
    023
    134
    201
    33 
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值