为了实现快速查找,map内部本身就是按序存储的(比如红黑树)。在我们插入<key, value>键值对时,就会按照key的大小顺序进行存储。这也是作为key的类型必须能够进行<运算比较的原因。现在我们用string类型作为key,因此,我们的存储就是按学生姓名的字典排序储存的。

【参考代码】

  1. #include<map>
  2. #include<string>
  3. #include<iostream>
  4. using namespace std;
  5. typedef pair<string, int> PAIR;
  6. ostream& operator<<(ostream& out, const PAIR& p) {
  7. return out << p.first << "\t" << p.second;
  8. }
  9. int main() {
  10. map<string, int> name_score_map;
  11. name_score_map["LiMin"] = 90;
  12. name_score_map["ZiLinMi"] = 79;
  13. name_score_map["BoB"] = 92;
  14. name_score_map.insert(make_pair("Bing",99));
  15. name_score_map.insert(make_pair("Albert",86));
  16. for (map<string, int>::iterator iter = name_score_map.begin();
  17. iter != name_score_map.end();
  18. ++iter) {
  19. cout << *iter << endl;    //因为重定义了输出<<操作符,否则用cout << iter->first << " => " << iter->second << '\n';
  20. }
  21. return 0;
  22. }

【运行结果】

大家都知道map是stl里面的一个模板类,现在我们来看下map的定义:

  1. template < class Key, class T, class Compare = less<Key>,
  2. class Allocator = allocator<pair<const Key,T> > > class map;

它有四个参数,其中我们比较熟悉的有两个: Key 和 Value。第四个是 Allocator,用来定义存储分配模型的,此处我们不作介绍。

现在我们重点看下第三个参数: class Compare = less<Key>

这也是一个class类型的,而且提供了默认值 less<Key>。 less是stl里面的一个函数对象,那么什么是函数对象呢?

所谓的函数对象:即调用操作符的类,其对象常称为函数对象(function object),它们是行为类似函数的对象。表现出一个函数的特征,就是通过“对象名+(参数列表)”的方式使用一个 类,其实质是对operator()操作符的重载。

现在我们来看一下less的实现:

  1. template <class T> struct less : binary_function <T,T,bool> {
  2. bool operator() (const T& x, const T& y) const
  3. {return x<y;}
  4. };

它是一个带模板的struct,里面仅仅对()运算符进行了重载,实现很简单,但用起来很方便,这就是函数对象的优点所在。stl中还为四则运算等常见运算定义了这样的函数对象,与less相对的还有greater:

  1. template <class T> struct greater : binary_function <T,T,bool> {
  2. bool operator() (const T& x, const T& y) const
  3. {return x>y;}
  4. };

map这里指定less作为其默认比较函数(对象),所以我们通常如果不自己指定Compare,map中键值对就会按照Key的less顺序进行组织存储,因此我们就看到了上面代码输出结果是按照学生姓名的字典顺序输出的,即string的less序列。

我们可以在定义map的时候,指定它的第三个参数Compare,比如我们把默认的less指定为greater:

【参考代码】

  1. #include<map>
  2. #include<string>
  3. #include<iostream>
  4. using namespace std;
  5. typedef pair<string, int> PAIR;
  6. ostream& operator<<(ostream& out, const PAIR& p) {
  7. return out << p.first << "\t" << p.second;
  8. }
  9. int main() {
  10. map<string, int, greater<string> > name_score_map;
  11. name_score_map["LiMin"] = 90;
  12. name_score_map["ZiLinMi"] = 79;
  13. name_score_map["BoB"] = 92;
  14. name_score_map.insert(make_pair("Bing",99));
  15. name_score_map.insert(make_pair("Albert",86));
  16. for (map<string, int>::iterator iter = name_score_map.begin();
  17. iter != name_score_map.end();
  18. ++iter) {
  19. cout << *iter << endl;
  20. }
  21. return 0;
  22. }

【运行结果】

现在知道如何为map指定Compare类了,如果我们想自己写一个compare的类,让map按照我们想要的顺序来存储,比如,按照学生姓名的长短排序进行存储,那该怎么做呢?

其实很简单,只要我们自己写一个函数对象,实现想要的逻辑,定义map的时候把Compare指定为我们自己编写的这个就ok啦。

  1. struct CmpByKeyLength {
  2. bool operator()(const string& k1, const string& k2) {
  3. return k1.length() < k2.length();
  4. }
  5. };

是不是很简单!这里我们不用把它定义为模板,直接指定它的参数为string类型就可以了。

【参考代码】

  1. int main() {
  2. map<string, int, CmpByKeyLength> name_score_map;
  3. name_score_map["LiMin"] = 90;
  4. name_score_map["ZiLinMi"] = 79;
  5. name_score_map["BoB"] = 92;
  6. name_score_map.insert(make_pair("Bing",99));
  7. name_score_map.insert(make_pair("Albert",86));
  8. for (map<string, int>::iterator iter = name_score_map.begin();
  9. iter != name_score_map.end();
  10. ++iter) {
  11. cout << *iter << endl;
  12. }
  13. return 0;
  14. }

【运行结果】

C++ STL中Map的按Key排序的更多相关文章

  1. C++ STL中Map的按Key排序和按Value排序

    map是用来存放<key, value>键值对的数据结构,可以很方便快速的根据key查到相应的value.假如存储学生和其成绩(假定不存在重名,当然可以对重名加以区 分),我们用map来进 ...

  2. C++ STL中Map的按Key排序跟按Value排序

    C++ STL中Map的按Key排序和按Value排序 map是用来存放<key, value>键值对的数据结构,可以很方便快速的根据key查到相应的value.假如存储学生和其成绩(假定 ...

  3. C++ STL中Map的按Value排序

    那么我们如何实现对pair按value进行比较呢? 第一种:是最原始的方法,写一个比较函数:  第二种:刚才用到了,写一个函数对象.这两种方式实现起来都比较简单. typedef pair<st ...

  4. C++ STL中Map的相关排序操作:按Key排序和按Value排序 - 编程小径 - 博客频道 - CSDN.NET

    C++ STL中Map的相关排序操作:按Key排序和按Value排序 - 编程小径 - 博客频道 - CSDN.NET C++ STL中Map的相关排序操作:按Key排序和按Value排序 分类: C ...

  5. C++中的STL中map用法详解(转)

    原文地址: https://www.cnblogs.com/fnlingnzb-learner/p/5833051.html C++中的STL中map用法详解   Map是STL的一个关联容器,它提供 ...

  6. C++ STL 中 map 容器

    C++ STL 中 map 容器 Map是STL的一个关联容器,它提供一对一(其中第一个可以称为关键字,每个关键字只能在map中出现一次,第二个可能称为该关键字的值)的数据 处理能力,由于这个特性,它 ...

  7. STL中map的使用

    知识点 C++中map提供的是一种键值对容器,里面的数据都是成对出现的.map内部自建一颗红黑树(一种非严格意义上的平衡二叉树),这颗树具有对数据自动排序的功能,所以在map内部所有的数据都是有序的. ...

  8. STL中map与hash_map的比较

    1. map : C++的STL中map是使用树来做查找算法; 时间复杂度:O(log2N) 2. hash_map : 使用hash表来排列配对,hash表是使用关键字来计算表位置; 时间复杂度:O ...

  9. STL中map与hash_map容器的选择收藏

    这篇文章来自我今天碰到的一个问题,一个朋友问我使用map和hash_map的效率问题,虽然我也了解一些,但是我不敢直接告诉朋友,因为我怕我说错了,通过我查询一些帖子,我这里做一个总结!内容分别来自al ...

随机推荐

  1. springMVC中Unknown return value type: java.lang.Integer(解决)

    controller层返回值类型为Integer,然而报 Unknown return value type: java.lang.Integer 这个错误,500错误 解决办法:在此方法上写上注解@ ...

  2. Java基于数据源的数据库访问

    ☞ 概述 最早接触的Java访问数据库,是通过jdbc接口.后来工作之后,一般是在服务器(如weblogic)配置数据源,通过JNDI使用数据源:最近需要在程序中动态构造数据源,查了些资料,备录于此. ...

  3. CentOS7编译安装PostgreSQL

    创建组和用户 groupadd postgres useradd -g postgres postgres passwd postgres 编译安装 yum install -y gcc gcc-c+ ...

  4. uva 10648(简单dp)

    Recently one of my friend Tarik became a member of the food committee of an ACM regional competition ...

  5. 【POJ 3784】 Running Median (对顶堆)

    Running Median Description For this problem, you will write a program that reads in a sequence of 32 ...

  6. BZOJ 3997 [TJOI2015]组合数学(单调DP)

    [题目链接] http://www.lydsy.com/JudgeOnline/problem.php?id=3997 [题目大意] 给出一个网格图,其中某些格子有财宝,每次从左上角出发,只能向下或右 ...

  7. BZOJ 1229 [USACO2008 Nov]toy 玩具(三分+贪心)

    [题木链接] http://www.lydsy.com/JudgeOnline/problem.php?id=1229 [题目大意] 每天对玩具都有一定的需求ni,每天可以花f价值每条购买玩具, 当天 ...

  8. 【Java】【滚动数组】【动态规划】UVA - 11137 - Ingenuous Cubrency

    滚动数组优化自己画一下就明白了. http://blog.csdn.net/u014800748/article/details/45849217 解题思路:本题利用递推关系解决.建立一个多段图,定义 ...

  9. canvas之arcTo

    arc与arcTo,从名字都能看出来相似.arcTo也是画曲线的方法,而且他画出的曲线也是正圆的一段弧线.但他的参数和arc简直是不共戴天~ ctx.arcTo(x1,y1,x2,y2,radius) ...

  10. python获取函数名

    Date: 20140223Auth: Jin 参考: http://hi.baidu.com/greysign/item/d11919d325c4c2e6b2f777bf 获取函数名python中获 ...