<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    PS,1880后程序員

    看不完的牙,寫不完的程序,跑不完的步。
    隨筆 - 97, 文章 - 34, 評論 - 10, 引用 - 0
    數據加載中……

    C++ Primer 之 讀書筆記 第十章

     

    關聯容器 Associative Containers

     

    關聯容器包括:

    l  map

    l  set

    l  multimap

    l  multiset

     

    10.1 初步知識:pair類型

    創(chuàng)建和初始化pairs

    Examples:

    pair<string, string> anon;       // holds two strings

    pair<string, int> word_count;    // holds a string and an int

    pair<string, vector<int> > line; // holds string and vector<int>

    使用typedef簡化定義:

    typedef pair<string, string> Author;

    Author proust("Marcel", "Proust");

    Author joyce("James", "Joyce");

    pair操作

    可以直接訪問pair的數據成員。這些數據成員都是public。(the pair class gives us direct access to its data members: Its members are public.

    string firstBook;

    // access and test the data members of the pair

    if (author.first == "James" && author.second == "Joyce")

        firstBook = "Stephen Hero";

     

    10.2 關聯容器

    關聯容器共享了很多順序容器的操作。但是關聯容器還定義了自己特有的操作。

    關聯容器的元素是按key進行排序的。當我們迭代訪問一個關聯容器時,保證是按照key的順序來訪問,而不是按照元素在容器中的順序來訪問的。When we iterate across an associative container, we are guaranteed that the elements are accessed in key order, irrespective of the order in which the elements were placed in the container.

     

    10.3 map

    定義map

    map<k, v> m;

    創(chuàng)建一個名字是m的空的map

    map<k, v> m(m2);

    創(chuàng)建一個名字是mmapmm2的拷貝。mm2必須具有相同的keyvalue類型。

    map<k, v> m(b, e);

    創(chuàng)建一個名字是mmap,它是迭代器be指定的元素的拷貝。元素的類型必須可以轉換成<const k, v>

     

    key類型的約束條件

    key不僅僅有類型,而且還包括對比方法。缺省條件下,使用>操作符比較key。這就是說,作為key的類型必須定義<操作。

    map定義的類型

    map定義的類型包括:

    map<K, V>::key_type

    用于索引mapkey的類型

    map<K, V>::mapped_type

    map中與key關聯的 值的類型

    map<K, V>::value_type

    pair

    它的第一個元素的類型必須是constmap<K, V>::key_type;第二個元素的類型必須是map<K, V>::mapped_type

    value_type是一個pair,只能修改pair的值,而不能修改key

    map迭代器解引用生成pair

    當我們解引用一個map迭代器,得到的是一個容器值的引用, 這個值的類型是value_type類型。

    Example:

    // get an iterator to an element in word_count

    map<string, int>::iterator map_it = word_count.begin();

     

    // *map_it is a reference to a pair<const string, int> object

    cout << map_it->first;                  // prints the key for this element

    cout << " " << map_it->second;          // prints the value of the element

    map_it->first = "new key";              // error: key is const

    ++map_it->second;     // ok: we can change value through an iterator

     

    map添加元素

    2種方法:

    l  使用insert

    l  先用下標操作符索引元素,然后對此元素進行賦值。

    通過下標索引map

    map中下標就是key。如果使用的下標值不存在,就會在map里追加一個元素,它的key就是這個下標值。

    map <string, int> word_count; // empty map

    // insert default initialzed element with key Anna; then assign 1 to its value

    word_count["Anna"] = 1;

    map下標操作的返回值類型是mapped_value

    使用map::insert

    一個簡單的例子可以看出insert和下標操作的區(qū)別:

    int main() {

                map <string, int> word_count ;

                word_count["first"] =1;

                word_count["first"] =9;

                cout << word_count["first"] << endl;

                word_count.clear();

                word_count.insert( map<string, int>::value_type("first", 1) );

                word_count.insert( map<string, int>::value_type("first", 9) );

                cout << word_count["first"] << endl;

      return 0;

    }

    輸出:

    9

    1

    insert返回的是一個pairfirst是指向元素的map迭代器,secondbool值,表示元素是否插入成功。如果key存在時,直接返回map中的元素迭代器;如果key不存在,創(chuàng)建一個新的pair,然后插入map,返回這個新元素對應的迭代器。

    map查找

    下標操作提供了最簡單的訪問獲得鍵值的方法:

    map<string,int> word_count;

    int occurs = word_count["foobar"];

    int occurs = word_count["foobar"];但是這樣的取值方法其實還有可能隱含著一個插入操作。如果word_count不包含"foobar",則先插入以"foobar"作為key的元素。值則是按默認值處理,等于0,這樣occurs就被賦值為0.

    另一類方法:

    m.count(k)

    返回km中出現的次數

    m.find(k)

    如果k存在,返回指向該元素的迭代器。如果不存在,返回off-the-end迭代器。

    先用這類方法進行判斷,然后再用下班取值,就可以避免如果key不存在,直接取值導致向map插入元素帶來的副作用。

    Example(使用count檢查某個key是否存在):

    int occurs = 0;

    if (word_count.count("foobar"))

        occurs = word_count["foobar"];

    Example(讀取元素而不插入元素):

    int occurs = 0;

    map<string,int>::iterator it = word_count.find("foobar");

    if (it != word_count.end())

        occurs = it->second;

    刪除map元素

    有三類刪除元素的操作:

    m.erase(k)

    刪除key值是k的元素。返回值的類型是size_type,表示刪除元素的個數。

    m.erase(p)

    刪除由迭代器p指向的元素。p!=m.end()。返回值是void

    m.erase(b,e)

    刪除由迭代器b,e指定訪問內的所有元素。返回值是void

     

    10.4 set

    其實就是只有keymap

     

    10.5 multimap multiset 類型

    multimap追加元素,還是按照pair來追加的。

    // adds first element with key Barth

    authors.insert(make_pair(

      string("Barth, John"),

      string("Sot-Weed Factor")));

     

    // ok: adds second element with key Barth

    authors.insert(make_pair(

      string("Barth, John"),

      string("Lost in the Funhouse")));

     

    multimapfind操作

    find的返回值是迭代器:

    // author we'll look for

    string search_item("Alain de Botton");

     

    // how many entries are there for this author

    typedef multimap<string, string>::size_type sz_type;

    sz_type entries = authors.count(search_item);

     

    // get iterator to the first entry for this author

    multimap<string,string>::iterator iter =

                             authors.find(search_item);

     

    // loop through the number of entries there are for this author

    for (sz_type cnt = 0; cnt != entries; ++cnt, ++iter) cout <<

           iter->second << endl; // print each title

    對比mapfind操作:

    //int occurs = 0;

    map<string,int>::iterator it = word_count.find("foobar");

    if (it != word_count.end())

        occurs = it->second;

     

    另一種面向迭代器的解決方案

    這種方案包含了3種操作,這3種操作返回值都是指針。它們提供了另一種訪問集合元素的方法,雖然這些方法對于mapset也適用,但是更多情況還是用在multimapmultiset

    m.lower_bound(k)

    返回指向key值不小于k的第一個元素的迭代器。

    m.upper_bound(k)

    返回指向key值大于k的第一個元素的迭代器

    m.equal_range(k)

    返回一個迭代器的pair

    first相當于m.lower_bound(k)

    second相當于m. upper_bound(k)

    例如,key數據如下:

    1

    2

    3

    3

    5

    6

    6

    7

    7

    7

    8

    If key=3, lower_bound=第一個3; upper_bound=5

    if key=4; lower_bound=第一個5; upper_bound=5。這表明此key不存在(判斷條件lower_bound= upper_bound),同時也表示出這個key在容器中的插入位置。

     

    使用容器:文本查詢程序

    這部分其實最好先自己寫寫看。

    需求:

    讀入指定文件,然后統計指定單詞出現的次數,按規(guī)定的格式來顯示。

    規(guī)定格式包括:

    l  出現的總的次數

    l  行號 內容

    按照這個要求我先寫了一個,然后再回去讀大師的說法,比對不足。

     

     

     

     

     

    posted on 2009-06-04 11:22 amenglai 閱讀(836) 評論(0)  編輯  收藏 所屬分類: C++ Primer 之 讀書筆記

    主站蜘蛛池模板: 美女被艹免费视频| 无码免费午夜福利片在线| 伊人久久综在合线亚洲2019| 青青草a免费线观a| 成年网站免费入口在线观看| 久久亚洲成a人片| 热久久精品免费视频| 3344在线看片免费| 亚洲欧美日韩中文二区| 久久伊人亚洲AV无码网站| 在线观看免费人成视频色| 一区二区三区免费高清视频| 亚洲国产成人精品青青草原| 亚洲AV无码乱码在线观看性色扶| 日本在线免费观看| 福利片免费一区二区三区| 久久久亚洲欧洲日产国码二区 | 亚洲乱理伦片在线观看中字| 亚洲综合色婷婷七月丁香| 日韩欧美一区二区三区免费观看| 黄床大片免费30分钟国产精品 | 亚洲欧美日韩国产成人| 亚洲国产综合专区电影在线| 免费在线黄色网址| 国产精品成人免费一区二区 | 国产jizzjizz免费视频| 99久久精品免费精品国产| 日韩a毛片免费观看| 亚洲欧美国产精品专区久久| 亚洲一区影音先锋色资源| av在线亚洲欧洲日产一区二区| 成人浮力影院免费看| 免费网站观看WWW在线观看| 美女黄色免费网站| 亚洲日韩看片无码电影| 亚洲福利视频网址| 亚洲AV无码成人网站久久精品大 | 精品国产亚洲一区二区三区| 日韩中文无码有码免费视频| 蜜桃AV无码免费看永久| a视频免费在线观看|