map和multimap映射容器
map容器
map所處理的數據與數據庫表具有鍵值的記錄非常相似,在鍵值與映射數據之間,建立一個數學上的映射關系。map容器的數據結構仍然採用紅黑樹進行管理。插入的元素鍵值不同意反復,所使用的結點元素的比較函數僅僅對元素的鍵值進行比較,元素的各項數據能夠通過鍵值檢索出來。對於鍵值和映射數據。能夠通過pair封裝成一個結構對象。map要做的就是將這個pair對象插入到紅黑樹中,同一時候也須要提供一個僅使用鍵值進行比較的函數對象,將它傳遞給紅黑樹。此時就能夠利用紅黑樹的操作將map元素插入到二叉樹的正確位置。並對其進行元素的刪除和檢索。map與set的差別主要在於,map處理的是帶有鍵值的記錄型元素數據的高速插入、刪除和檢索,而set
創建map對象
主要有下面幾種方式。
(1) map()
創建一個空的map對象,元素的鍵值類型為char,元素的映射數據類型為int,鍵值的比較函數對象為greater<char>
map<char,int,grater<char>> m;
(2) map(const key_compare&cmp)
struct strLess{
bool operator()(const char* s1,const char*s2)const
{
return strcmp(s1,s2)<0;
}
};
map<const char*,int> m(strLess());
(3) map(const map&)
拷貝構造函數。
map<int,char*> m1;
map<int,char*> m2(m1);
(4) map(InputIteratorfirst,InputIterator last)
pair<const int,char> p1(1,‘a‘);
pair<const int,char> p2(2,‘b‘);
pair<const int,char> p3(3,‘c‘);
pair<const int,char> p4(4,‘d‘);
pair<const int,char> array[]={p1,p2,p3,p4};
map<const int,char> m(array,array+4);
(5) map(InputIteratorfirst,InputIterator last, const key_compare&cmp)
map<const int,char,greater<const int>>m(array,array+4,greater<const int>());
元素的插入
元素的插入主要利用insert函數,利用數組操作也能夠顯式地為map賦值。可是不能檢測是否插入成功。
#include<iostream> #include<map> using namespace std; int main() { map<const char*,float> m; m["apple"]=1.5f; m["orange"]=2.0f; m["banana"]=1.1f; cout<<"蘋果價格:"<<m["apple"]<<"元/斤"<<endl; cout<<"橘子價格:"<<m["orange"]<<"元/斤"<<endl; cout<<"香蕉價格:"<<m["banana"]<<"元/斤"<<endl; return 0; }
元素的刪除
與set集合容器一樣,map容器能夠刪除某個叠代器位置上的元素。等於某個鍵值的元素。一個叠代器區間上的元素和容器中的全部元素。erase函數和clear函數。
元素的遍歷
map元素的遍歷除了利用鍵值的數組方式來訪問元素,還能夠使用叠代器的方式進行訪問。
#include<iostream> #include<map> using namespace std; struct stuInfo{ char *name; int age; }; struct stuRecord{ int id; stuInfo sf; }; int main() { stuRecord sArray[]={{1,"li",20},{10,"shi",18},{3,"wang",21}}; map<int,stuInfo> m; for(int i=0;i<3;i++) { m[sArray[i].id]=sArray[i].sf; } map<int,stuInfo>::iterator begin,end; end=m.end(); cout<<"學號 "<<"姓名 "<<"年齡 "<<endl; for(begin=m.begin();begin!=end;begin++) { cout<<(*begin).first<<" " <<(*begin).second.name<<" " <<(*begin).second.age<<" " <<endl; } return 0; }
從結果能夠看出,盡管是無序插入的,可是遍歷出的結果是有序的。
元素的搜索
利用find函數能夠搜索出具有某一鍵值的元素。
#include<iostream> #include<map> using namespace std; struct stuRecord{ struct stuInfo{ char *name; int age; }; stuRecord(int id_,char *name_,int age_) { id=id_; sf.name=name_; sf.age=age_; } int id; stuInfo sf; }; int main() { typedef map<int,stuRecord::stuInfo> stuMap; stuMap m; pair<stuMap::iterator,bool> p; //插入第一條學生記錄 stuRecord stu1=stuRecord(5,"li",22); pair<int,stuRecord::stuInfo> pairStu1(stu1.id,stu1.sf); p=m.insert(pairStu1); if(!p.second) cout<<"插入學生記錄失敗\n"; //插入第二條學生記錄 stuRecord stu2=stuRecord(1,"shi",20); pair<int,stuRecord::stuInfo> pairStu2(stu2.id,stu2.sf); p=m.insert(pairStu2); if(!p.second) cout<<"插入學生記錄失敗\n"; //插入第三條學生記錄 stuRecord stu3=stuRecord(10,"zhang",21); pair<int,stuRecord::stuInfo> pairStu3(stu3.id,stu3.sf); p=m.insert(pairStu3); if(!p.second) cout<<"插入學生記錄失敗\n"; //搜索 stuMap::iterator i=m.find(5); cout<<"搜索學號為5的記錄:\n" <<(*i).first<<‘ ‘ <<(*i).second.name<<‘ ‘ <<(*i).second.age<<‘ ‘<<endl; return 0; }
map還提供其它的函數,empty、size、swap、lower_bound、upper_bound、equal_range等。
multimap多重映射容器
multimap容器也是用紅黑樹對記錄型元素數據依照鍵值的比較關系進行高速的插入、刪除、檢索,元素的檢索是對數級的時間復雜度,與map不同的是,multimap同意將具有反復鍵值的元素插入容器,元素的鍵值與元素的映射數據的映射關系是多對多的。
創建multimap對象
有下面幾種方式。
(1) multimap()
multimap<char,int,greater<char>>mm;
(2) multimap(constkey_compare&cmp)
struct strLess{
bool operator()(const char *s1,const char*s2)const
{
return strcmp(s1,s2)<0;
}
};
multimap<constchar*,int> mm(strLess());
(3) multimap(const map&)
multimap<int,char*> mm1;
multimap<int,char*> mm2(mm1);
(4) multimap(InputIteratorfirst,InputIterator last)
pair<constint,char> p1(1,‘a‘);
pair<constint,char> p2(1,‘e‘);
pair<constint,char> p3(2,‘b‘);
pair<constint,char> p4(3,‘c‘);
pair<constint,char> pairArray[]={p1,p2,p3,p4};
multimap<constint,char> mm(pairArray,pairArray+4);
(5) multimap(InputIteratorfirst,InputIterator last, const key_compare&cmp)
multimap<constint,char,greater<const int>> mm(pairArray,pairArray+4,greater<constint>());
元素的插入
multimap容器僅僅能使用insert函數插入元素到容器的紅黑樹中。
multimap<float,char *> mm;
mm.insert(pair<float,char*>(3.0f,"apple"));
mm.insert(pair<float,char*>(3.0f,"pear"));
mm.insert(pair<float,char*>(2.1f,"orange"));
mm.insert(pair<float,char*>(1.5f,"banana"));
元素的刪除
與map集合容器一樣。map容器能夠刪除某個叠代器位置上的元素。等於某個鍵值的元素,一個叠代器區間上的元素和容器中的全部元素,erase函數和clear函數。
元素的遍歷
multimap容器的遍歷,能夠用叠代器來實現。
#include<iostream> #include<map> using namespace std; int main() { multimap<float,char *> mm; mm.insert(pair<float,char *>(3.0f,"apple")); mm.insert(pair<float,char *>(3.0f,"pear")); mm.insert(pair<float,char *>(2.1f,"orange")); mm.insert(pair<float,char *>(1.5f,"banana")); multimap<float,char *>::iterator begin,end; end=mm.end(); for(begin=mm.begin();begin!=end;begin++) { cout<<(*begin).second<<" "<<(*begin).first<<"元/斤"<<endl; } cout<<endl; return 0; }
反向遍歷
利用反向叠代器能夠實現逆向遍歷。
#include<iostream> #include<map> using namespace std; int main() { multimap<float,char *> mm; mm.insert(pair<float,char *>(3.0f,"apple")); mm.insert(pair<float,char *>(3.0f,"pear")); mm.insert(pair<float,char *>(2.1f,"orange")); mm.insert(pair<float,char *>(1.5f,"banana")); multimap<float,char *>::reverse_iterator rbegin,rend; rend=mm.rend(); for(rbegin=mm.rbegin();rbegin!=rend;rbegin++) { cout<<(*rbegin).second<<" "<<(*rbegin).first<<"元/斤"<<endl; } return 0; }
元素的搜索
multimap容器的find函數將返回第一個搜索到的元素的位置,假設元素不存在將返回end結束元素位置。
其它經常使用函數
其它經常使用函數有empty、size、count、lower_bound、upper_bound等。
#include<iostream> #include<map> using namespace std; int main() { multimap<int,char> mm; cout<<mm.size()<<endl; mm.insert(pair<int,char>(3,‘a‘)); mm.insert(pair<int,char>(3,‘c‘)); mm.insert(pair<int,char>(1,‘b‘)); mm.insert(pair<int,char>(2,‘d‘)); mm.insert(pair<int,char>(3,‘e‘)); mm.insert(pair<int,char>(4,‘g‘)); cout<<mm.count(3)<<endl; cout<<mm.size()<<endl; return 0; }
map和multimap映射容器