c++对map进行排序

原创 2016年05月31日 15:05:11

          最近在PAT刷题,其中一道题月饼 (25)需要用到对价格进行排序,但是排序后要用到价格对应的总售价。因而可以考虑用关联容器进行求解,map是比较合适这题的数据结构。

        map是用来存放<key, value>键值对的数据结构,可以很方便快速的根据key查到相应的value。关于map的详细定义及用法可以见C++STL之map学习。假如存储学生和其成绩,我们用map来进行存储就是个不错的选择。 我们这样定义map<string, int>,其中学生姓名用string类型,作为Key;该学生的成绩用int类型,作为value。我们可以根据学生姓名快速的查找到他的成绩。另一方面,如果我们想把所有同学和他相应的成绩都输出来,并且按照我们想要的顺序进行输出:比如按照学生姓名的顺序进行输出,或者按照学生成绩的高低进行输出。换句话说,我们希望能够对map进行按Key排序或按Value排序。本文对这两种排序进行一个简单的总结。


一、按Key排序

       我们知道,map内部本身就是按序存储的(比如红黑树),这样方便实现快速查找。在我们插入<key, value>键值对时,map就会自动按照key的大小顺序进行存储。因而作为key的类型必须能够进行大小运算的比较。比如int、double、string、char等类型。以月饼 (25)这一题为背景例子进行编程说明。

//按Key排序
#include<iostream>
#include<vector>
#include<map>
#include<iomanip>

using namespace std;  

int main()
{
	double N,maxneed,tm,ts;
	cin>>N>>maxneed;
	vector<double> vm,vs,vp;//vm是总量,vs是总销售额,vp是价格
	for(int i = 1;i<=N;++i)
	{
		cin>>tm;
		vm.push_back(tm);
	}
	for(int i = 1;i<=N;++i)
	{
		cin>>ts;
		vs.push_back(ts);
	}
	for(int i = 0;i<N;++i)
		vp.push_back(vs[i]/vm[i]);

	map<double,double> m;
	for(int i = 0;i<N;++i)
		m.insert(make_pair(vp[i],vs[i]));//插入后自动按Key值进行排序
	cout<<"按Key排序结果:"<<endl;
	for(map<double,double>::iterator it=m.begin();it!=m.end();++it)
		cout<<it->first<<" "<<it->second<<endl;

	system("pause");
	return 0;
}

结果如下:


       从结果可以看到未对map进行任何操作,它按照Key值自动进行了排序。

       具体到月饼 (25)这一题上,详细分析可以见另外一篇博客PAT上面一道关于“月饼”的题目的解法

       另举一例进行说明:

#include<iostream>
#include<map>  
#include<string>  
  
using namespace std;  
  
typedef pair<string, int> PAIR;  
  
ostream& operator<<(ostream& out, const PAIR& p) 
{  
	return out << p.first << "\t" << p.second;  
}  
  
int main() 
{  
	map<string, int> name_score_map;  
	name_score_map["LiMin"] = 90;   
    name_score_map["ZiLinMi"] = 79;   
    name_score_map["BoB"] = 92;   
    name_score_map.insert(make_pair("Bing",99));  
    name_score_map.insert(make_pair("Albert",86));  
    for (map<string, int>::iterator iter = name_score_map.begin();  
		iter != name_score_map.end();  
		++iter) {  
		cout << *iter << endl;  
	}  
	system("pause");
	return 0;  
 } 
结果如下:


上面的按key值排序有个缺点:即当插入的有多个相等的值时,由于key的唯一性,会只保留一个。因此月饼 (25)这一题不适合用按key进行排序求解(因为不排斥某两种月饼的价格相等)。


二、按Value排序

        如何实现Map的按Value排序呢?

        第一反应是利用STL中提供的sort算法实现,这个想法是好的,不幸的是,sort算法有个限制,利用sort算法只能对序列容器进行排序,就是线性的(如vector,list,deque)。map是一个集合容器,它里面存储的元素是pair,但是它不是线性存储的(像红黑树),所以利用sort不能直接和map结合进行排序。因而可以采用一些其它的思路,总结如下:


思路1:可以考虑将value作为key值进行自动排序。

思路2:可以把map中的key值和value值分别转存到一个pair类型的vector中,在对vector按照一定的规则排序即可。这样的方法对值一样的情况也能够使用。具体代码如下:

//功能:输入单词,统计单词出现次数并按照单词出现次数从多到少排序  
#include <iostream>
#include <cstdlib>  
#include <map>  
#include <vector>  
#include <string>  
#include <algorithm>  

using namespace std;
   
int cmp(const pair<string, int>& x, const pair<string, int>& y)  
{  
	return x.second > y.second;  
}  
   
void sortMapByValue(map<string, int>& tMap,vector<pair<string, int> >& tVector)  
{  
	for (map<string, int>::iterator curr = tMap.begin(); curr != tMap.end(); curr++)   
		tVector.push_back(make_pair(curr->first, curr->second));    
   
	sort(tVector.begin(), tVector.end(), cmp);  
}  
int main()  
{  
	map<string, int> tMap;  
	string word;  
	while (cin >> word)  
	{  
		pair<map<string,int>::iterator,bool> ret = tMap.insert(make_pair(word, 1));  
		if (!ret.second)  
			++ret.first->second;  
	}   
   
	vector<pair<string,int>> tVector;  
	sortMapByValue(tMap,tVector);  
	for(int i=0;i<tVector.size();i++)  
		cout<<tVector[i].first<<": "<<tVector[i].second<<endl;  
   
	system("pause");  
	return 0;  
}  

结果如下:



参考资料

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

C++STL之map学习

STL中map按值(value)排序

对map集合进行排序

STL容器(三)——对map排序

如何禁止STL map 自动排序

版权声明:本文为博主原创文章,未经博主允许不得转载。

相关文章推荐

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

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

STL中map按值(value)排序

文中的部分内容参考自互联网,感谢作者。 map默认是按照键(key)排序的。很多时候我们需要按值(value)排序,靠map里的算法当然是不行的,那么可以把它转存到vector中,在对vector按照...

C++STL之map学习

map   map是一种关联容器,存储相结合形成的一个关键值和映射值的元素。Map 是一种Pair Associative Container,意味着它的值类型为 pair. 而且也是 Un...

搜狗面试的经典题(C++map按值排序,class struct的区别)

一:起因 (1)java  Map排序(key,value),请看另一篇博客 java Map排序  (2)c++ map排序(key,value),可以对c++ map和java Map进行对比:之...

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

C++ STL中Map的按Key排序和按Value排序, 实用方法小结!

数据库day02

day01回顾一、数据库存储、管理和维护数据的集合 DB DBMS二、SQL语言DDL:对对象进行操作(数据库、表、列)CREATE、ALTER、DROPDML:对表中的数据进行操作INSERT、...

c++ 自定义排序函数的 map

c++ 自定义排序函数的 map   bcb struct datekey {     unsigned __int64 i;     String s;     boo...

C++中map按value排序

我们知道C++ STL中的map是以key排序的。int main() { map iMap; iMap[1] = 20; iMap[2] = 10; iMap[5] ...

C++:泛型编程(看病要排队)

C++:泛型编程(看病要排队) Time Limit(Common/Java):1000MS/3000MS Memory Limit:65536KByte Description 看病要排队...

C++按map的value进行排序

C++中,map是按key值大小排序存储。有时候,我们需要对map的value进行排序,根据value的大小顺序获得key的序列。比较简单的方法就是,重新定义一个新的map,新map的key和valu...
  • IDMer
  • IDMer
  • 2017-01-04 19:45
  • 1358
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:深度学习:神经网络中的前向传播和反向传播算法推导
举报原因:
原因补充:

(最多只允许输入30个字)