std map的安全遍歷並刪除元素的方法

2021-10-04 12:31:29 字數 1526 閱讀 7857

首先我們講遍歷std::map, 大部分人都能寫出第一種遍歷的方法,但這種遍歷刪除的方式並不太安全。

第一種 for迴圈變數:

#include#include#includeusing namespace std;

int main()

return 0;

}

結果如下:

key: 0 value: 5555555555555555

key: 1 value: 1111111111111111

key: 2 value: 2222222222222222

key: 3 value: 3333333333333333

key: 4 value: 4444444444444444

第二種while迴圈的遍歷:

#include #include #include #include using namespace std;

struct ltstr

};int main()

}

執行結果:

erasing: bart, 11

erasing: homer, 38

erasing: lisa, 8

erasing: maggie, 1

erasing: marge, 37

第三種更安全的for 迴圈遍歷:

#include#include#includeusing namespace std;

int main()

return 0;

}

執行結果與第一種方式相同,不過這種刪除方式也是stl原始碼一書中推薦的方式,分析 m.erase(it++)語句,map中在刪除iter的時候,先將iter做快取,然後執行iter++使之指向下乙個結點,再進入erase函式體中執行刪除操作,刪除時使用的iter就是快取下來的iter(也就是當前iter(做了加操作之後的iter)所指向結點的上乙個結點)。

根據以上分析,可以看出(m.erase(it++) )和(m.erase(it); iter++; )這個執行序列是不相同的。前者在erase執行前進行了加操作,在it被刪除(失效)前進行了加操作,是安全的;後者是在erase執行後才進行加操作,而此時iter已經被刪除(當前的迭代器已經失效了),對乙個已經失效的迭代器進行加操作,行為是不可預期的,這種寫法勢必會導致 map操作的失敗並引起程序的異常。

#include #include int main()

, , ,

, , };

// 從 c 擦除所有奇數

for(auto it = c.begin(); it != c.end(); )

if(it->first % 2 == 1)

it = c.erase(it);

else

++it;

for(auto& p : c)

std::cout << p.second << ' ';

}

std map迴圈遍歷刪除元素出現詭異現象

std mapm1,m1.insert std make pair 4,4 for auto it m1.begin it m1.end 這段 在執行的時候會出現if語句執行完繼續執行else語句。為什麼會出現這種現象?先來看一下map中的erase函式 可以看到erase並沒有返回值,不像vect...

QMap和std map的遍歷

兩種遍歷方式都使用迭代器 1qmap使用iterator.key 和iterator.value 方法獲取第乙個或第二個元素的值。而std map使用iterator first iterator second 來獲取第乙個或第二個元素的值。qmapm ratiocfg qmap iterator ...

std map 刪除指定條件的元素

在c 開發中,std map是經常使用到的容器,由鍵值就可以取出對應的值。在使用map時,如果想從map中刪除符合某一條件的元素,應該如何操作?我自己剛開始使用erase從迭代器中移除符合我需要刪除條件的鍵值對時,出錯了 include include int main return 0 出現了以下...