2017-06-14 53 views
-1

我想知道如果使用auto或其他類似聲明變量/ iterator/CallItWhatIsMoreAppropriate的東西)會每次都創建一個該項目的實例嗎?一個例子會說清楚:`auto`每次都創建一個新的變量實例?

void my_fun (std::unordered_map<std::string, std::string> & my_map) { 

    std::string search_str; 

    cin >> search_str; 

    while (search_str != "something") { 

     //Does the next line create an extra overhead each time? 
     auto search = my_map.find(search_str); 

     if (search != my_map.end()) 
     { 
      std::cout << "found \n"; 

      //I should be able to modify the element inside the map here. 

     } else { 
      my_map.insert({search_str, search_str}); 
     } 

     cin >> search_str; 

    } 

} 
+0

使用'auto'沒有任何開銷,並且您應該始終在可以正確初始化的地方定義變量。 –

+0

@NeilButterworth我認爲這是一個重要的問題,只有在需要時才聲明變量,然後使用該實例,特別是聲明在循環內可以運行數百萬甚至數十億次。 –

+6

「使用'auto'」在這裏並不意味着什麼。 'auto'只是類型名稱的替代品。你真正要問的是在循環中聲明一個_local變量_的後果。你的'search'是一個局部變量。這不是因爲你在聲明中使用了'auto';這是因爲你在哪裏宣佈它。 –

回答

3

考慮到這個特殊的代碼:

while (search_str != "something") { 

    //Does the next line create an extra overhead each time? 
    auto search = my_map.find(search_str); 

,如果你的意思是,如果有額外的開銷VS:

while (search_str != "something") { 
     //Does the next line create an extra overhead each time? 
     std::unordered_map<std::string, std::string>::iterator search = my_map.find(search_str); 

沒有沒有區別可言,只是編譯推導鍵入你。如果你詢問是否宣佈環路以外的迭代器:

std::unordered_map<std::string, std::string>::iterator search; 
    while (search_str != "something") { 
     search = my_map.find(search_str); 
     ... 

將使其更加高效,這在理論上是可能的(被碎編譯器),但我幾乎不懷疑會有什麼。代碼的可讀性在這裏更加重要,因爲在循環中聲明變量會使變量變得更清晰和更具可讀性。

注意更改search鍵入要麼const auto &要麼更明確const std::unordered_map<std::string, std::string>::iterator &也不太可能使它在這種情況下更有效。

+0

如果我想對地圖內的元素進行修改,我應該使用什麼? (const會使它不可編輯,對嗎?) –

+1

@AnnaK。你似乎誤解了'std :: unordered_map :: find()'返回的內容。它不是元素本身,而是迭代器。把它看作一種指針。所以,如果你聲明迭代器常量,這意味着你不能改變迭代器本身(例如使其指向另一個元素),但是這不會阻止更改它指向的元素。 – Slava

+0

感謝您向我闡明這一點。 –

2

是的。例如,使用const auto&auto&&來聲明一個引用,以防你想避免創建該對象的副本。

但是,迭代器幾乎沒有開銷,並且通常按值傳遞。

更重要的是,您按值傳遞參數my_map。按值傳遞將防止對該容器的任何更改從該函數外部可見(您正在編輯一個副本)。按引用傳遞以避免不必要的複製。

+2

'find'通過值返回一個迭代器,所以'auto&'只會創建一個綁定到臨時的const引用。在這裏使用'auto&'沒有任何好處。編輯:實際上,它似乎甚至沒有編譯('非參數的無效初始化...從右值...') – Kevin

+0

@Kevin是的,我更新爲使用'const auto&'。我的意圖是給出一個通用的例子,而不是這個例子中的確切答案。我也明確地解釋了迭代器在我的答案中最好通過value_。 – Snps

+0

爲什麼不用'auto &&'來代替? :) – Rakete1111

相關問題