map与hash_map使用与对比
#include <iostream> #include <functional> #include <map> #include <ext/hash_map> #include <string> using std::string; struct SInfo { string id_; string name_; SInfo(string id, string name):id_(id),name_(name){} }; // map example template<class T1> struct SLessThan : public std::binary_function<T1, T1, bool> { bool operator()(const T1 &first, const T1 &second) const { return first.id_ < second.id_; } }; void testmap() { std::cout<<"------------------- test map ----------------------------"<<std::endl; typedef std::map<SInfo, string, SLessThan<SInfo> > Info2IDMap; Info2IDMap info2IDMap; info2IDMap.insert(std::make_pair(SInfo("1001", "zhangsan"), "1001")); info2IDMap.insert(std::make_pair(SInfo("1004", "lisi"), "1004")); info2IDMap[SInfo("1003", "wanger")] = "1003"; for(Info2IDMap::iterator iter = info2IDMap.begin(); iter != info2IDMap.end(); ++iter) { std::cout<<iter->second<<";"; } std::cout<<std::endl; } // hash_map example typedef struct SHashInfo { size_t operator()(const SInfo &info) const { unsigned long __h = 0; for (size_t i = 0 ; i < info.id_.size() ; i ++) __h = 5*__h + info.id_[i]; return size_t(__h); } }SHashInfo; template<class T1> struct SEqual : public std::unary_function<T1, bool> { bool operator()(const T1 &first, const T1 &second) const { return first.id_ == second.id_; } }; void testhashmap() { std::cout<<"-------------------- test hash map -----------------------------"<<std::endl; typedef __gnu_cxx::hash_map< SInfo, string, SHashInfo, SEqual<SInfo> > Info2IDMap; Info2IDMap info2IDMap(11); info2IDMap[SInfo("10086", "beijing")] = "10086"; info2IDMap[SInfo("10085", "shanghai")] = "10085"; info2IDMap[SInfo("10087", "tianjin")] = "10087"; for(Info2IDMap::iterator iter = info2IDMap.begin(); iter != info2IDMap.end(); ++iter) { std::cout<<iter->second<<";"<<std::endl; } std::cout<<std::endl; } int main(int argc, char *argv[]) { testmap(); testhashmap(); return 0; }
通过上面的例子会发现:
1. map需要指定小于函数(可使用默认配置)。
2. hash_map需要指定哈希函数和等于函数。其中针对普通类型有通用配置。
3. hash_map还未被列入标准库中。
4. map的底层使用的是红黑树,因此可以保证数据有序,而hash_map的底层使用的是哈希表,不能保证数据有序。
疑问:map和hash_map的使用如何选择?
当数据量很大且hash冲突比较小,数据增删比较少,关心查询性能时使用hash_map;
增删数据较多的情况下使用map。
具体使用还需要根据具体场景判断,主要考虑:数据量,查询速度,内存占用(要注意对象构造速度,hash_map的慢)。