zoukankan      html  css  js  c++  java
  • 2、以自定义struct或struct指针作为map的Key

    若干问题

    struct Node {
        int k, b;
        friend bool operator <(Node a, Node b) {
            return a.k < b.k;
        }
    }node1, node2;
    
    map<Node, int> mp;
    
    
    int main() {
    
        node1.k = 1;
        node1.b = 1;
        mp[node1] = 1;
        node1.k = 1;
        node1.b = 2;
        printf("%d
    ", mp.count(node1));
        //输出1
        return 0;
    }
    View Code
    struct Node {
        int k, b;
        friend bool operator <(Node a, Node b) {
            if (a.k != b.k) return a.k < b.k;
            else return a.b < b.b;
        }
    }node1, node2;
    
    map<Node, int> mp;
    
    
    int main() {
    
        node1.k = 1;
        node1.b = 1;
        mp[node1] = 1;
        node1.k = 1;
        node1.b = 2;
        printf("%d
    ", mp.count(node1));
        //输出0
        return 0;
    }
    View Code

    1、以结构体为Key

    map内部自建一颗红黑树(一种非严格意义上的平衡二叉树),红黑树具有对数据自动排序(默认是以less<>升序对元素排序(排序准则也可以修改))的功能,因此在map内部所有的关键字都是有序的。当key为基本数据类型时,不存在问题。但是当关键字是一个结构体时,涉及到排序就会出现问题,因为它没有小于号操作,insert等函数在编译的时候就会出错,下面给出解决这个问题的方法:

    对操作符"<"进行重载(不可以重载大于号)

    #include <map>
    #include <iostream>
    #include <string>
    using namespace std;
    struct Node{
        int id;
        string  name;
        friend bool operator < (Node a,Node b) 
        {
            //指定排序策略,按id排序,如果id相等的话,按name排序
            if (a.id != b.id) return a.id > b.id;
            else return a.name > b.name;
        }
    }StudentInfo, *pStudentInfo;  //学生信息
    
    int main(){
        int nSize;
        //用学生信息映射分数
        map<Node, int> mapStudent;
        map<Node, int>::iterator it;
        
        StudentInfo.id = 1;
        StudentInfo.name = "student_one";
        mapStudent.insert(pair<Node, int>(StudentInfo, 90));
        StudentInfo.id = 1;
        StudentInfo.name = "student_two";
        mapStudent.insert(pair<Node, int>(StudentInfo, 80));
    
        for (it = mapStudent.begin(); it != mapStudent.end(); it++)
            cout << it->first.id << " " << it->first.name << " " << it->second << endl;
    
    }
    printf("%d",mp.find(StudentInfo)->second);
    printf("%d",mp[StudentInfo]);  都可以

    重载的部分可以写到结构体外,但有三点要求:

    1、把friend去掉,把小于号改成一对小括号。

    2、用struct把函数包装起来。

    3、map的定义方式改为map<Node, int, cmp> mapStudent;

    如:

    #include <map>
    #include <iostream>
    #include <string>
    using namespace std;
    struct Node{
        int id;
        string  name;
        
    }StudentInfo, *pStudentInfo;  //学生信息
    
    struct cmp {
        bool operator () (Node a, Node b)
        {
            //指定排序策略,按nID排序,如果nID相等的话,按strName排序
            if (a.id != b.id) return a.id > b.id;
            else return a.name > b.name;
        }
    };
    map<Node, int, cmp> mapStudent;
    map<Node, int, cmp>::iterator it;
    int main(){
        int nSize;
        //用学生信息映射分数
        
    
        
        StudentInfo.id = 1;
        StudentInfo.name = "student_one";
        mapStudent.insert(pair<Node, int>(StudentInfo, 90));
        StudentInfo.id = 1;
        StudentInfo.name = "student_two";
        mapStudent.insert(pair<Node, int>(StudentInfo, 80));
    
        for (it = mapStudent.begin(); it != mapStudent.end(); it++)
            cout << it->first.id << " " << it->first.name << " " << it->second << endl;
    
    }

     

    printf("%d",mp.find(StudentInfo)->second);
    printf("%d",mp[StudentInfo]); 也可以

    2、以结构体指针为Key,可以不重载<号,因为地址可以比较大小。

    但是也可以根据指针指向的内容重载小于号,但此时重载函数必须放在自定义的结构体外面。(原因不详。。。)

    #include <map>
    #include <iostream>
    #include <cstdio>
    using namespace std;
    
    struct Key
    {
        int x,y;
    }*ptr;
    
    struct CompareKey
    {
        bool operator()(Key *in_a, Key *in_b)
        {
            return in_a->x < in_b->x;
        }
    };
    
    map<Key *, int, CompareKey> mp;
    
    int main()
    {
    
        for (int i = 0; i < 10; i++)
        {
            Key *k = new Key;
            if(i==6) ptr=k;
    
            k->x = i;
            k->y = i+1;
    
            mp.insert(make_pair(k, i));
        }
    
        map<Key *, int, CompareKey>::iterator it;
        for(it=mp.begin();it!=mp.end();it++){
            if(it->first==ptr){
                printf("%d %d %d
    ",it->first->x,it->first->y,it->second);
            }
        }
    
    
    }
  • 相关阅读:
    Eclipse快捷键
    vs2010有哪些快捷键
    游戏引擎列表
    移动设备开发推荐网站(J2ME开发)
    Python入门学习资料推荐
    C#中常用的几种读取XML文件的方法
    Springboot整合RabbitMq
    JAVA获取上下行网速
    java jar 指定logback.xml、application.yaml
    在CentOS7系统安装与配置RabbitMQ
  • 原文地址:https://www.cnblogs.com/fuqia/p/9511994.html
Copyright © 2011-2022 走看看