10,一般意义下vector的元素是按顺序存储的,这就造成了,如果插入元素,则库将进行重新内存分配,并涉及到的旧vector的销毁。而实际中vector容器预留了这些额外的存储区用于存放新添加的元素。因此在实际上,比起list与deqeue容器,vector的增长效率通常会更高。
11,vector容器实际空间可能会比元素所占的空间更大,capacity成员函数用于返回容器实际的容量大小,一般比size要大。如果一直往vector内插入元素,则直到size==capacity之间,vector都不用重新进行内存分配。但如果再往里插入元素时,将又会重新分配,capacity又会比size大。
二、 关联容器
1,pair类型:
pair<string, string> name("ronny", "young"); // 定义并初始化 name = make_pair("ronny", "young"); string fullName = name.first + name.second;
2,关联容器
1)关联容器map实际上是装有n个pair类型的集合。map定义了三个类型别名,key_type、mapped_type、value_type分别表示键的类型、键所关联的值的类型和map里pair类型。
2)当使用下标访问map的值时,如果下标不存在,则导致在map中新添一个新的元素,它的键即为该下标值。
3)map的迭代器指向的是pair类型,所以当对迭代器解引用时,得到的是一个pair类型。这与下标得到的类型不同。
4)统计单词出现次数的例子:
map<string, int> word_cnt; string word; while (cin >> word) { ++word_cnt[word]; }
5)利用insert返回的类型来重写上面的,insert返回了一个pair类型,它的first成员为一个迭代器,而second成员为一个bool变量,表明该元素是否被插入。
map<string, int> word_cnt; string word; while (cin >> word) { pair<map<string, int>::iterator, bool> ret = word_cnt.insert(make_pair(word, 1)); if (!ret.second) ++(ret.first)->second; }
6)set容器是一个集合,它存储了键,且惟一不能修改。set的操作与map基本一致,只是没有mapped_type,而且vale_type就是key_type。在使用insert时,返回的也是pair类型的值。set不提供下标操作,只能使用find来查找元素是否存在,并且返回一个迭代器,如果不存在,则返回指向最后一个元素下一个的迭代器(end)。如果简单的判断某个键是否存在,则可以直接使用cout函数,它返回1或0。
7)multimap与multiset容器允许一个键值对应多个实例,实际上一个键值的多个实例是按顺序存储在一起的。它们的find的操作返回键值第一个实例的迭代器,cout返回键值有多少个实例。另外lower_bound与upper_bound分别用于返回所查找键值的第一个实例我迭代器与最后一个实例迭代器的下一位。
multimap<string, string> books; typedef multimap<string, string>::iterator authors_it; string search_item = "matin"; authors_it beg = books.lower_bound(search_item); authors_it end = books.upper_bound(search_item); while (beg != end) { cout << (beg++)->second << endl; }
更加方便的是equal_range函数,它返回了一个迭代器的pair对象,其实正好放着lower_bound和upper_bound