2016-09-18 494 views
2

我想創建std::string,其中包含由某個分隔符(可以來自STL或Boost)分隔的第一個元素std::map<std::string, std::string>。 有沒有比循環更好的解決方案(一行)?像boost::algorithm::joinstd::vector<std::string>std :: map <string,string>轉換爲字符串(第一個值)

+1

現在還不清楚。假設你有一個包含兩個元素的地圖。你正在尋找的輸出是類似「key1:value1,key2:value2」? – Rerito

+0

請參閱[如何從std :: map檢索所有鍵(或值)?](http://stackoverflow.com/questions/110157/how-to-retrieve-all-keys-or-values-from-a -stdmap),修改解決方案以附加到字符串 –

+0

不,@Rerito。對於:「key1:value1,key2:value2」和逗號分隔符我想要:「key1,key2」。 – peter55555

回答

1

你的算法應該是這樣的:

std::string get_keys(const std::map<std::string, std::string>& map) { 
    std::string result; 
    std::for_each(map.cbegin(), 
       map.cend(), 
       [&result](const decltype(map)::value_type& p) { 
        result += p.first; 
        result += ", "; 
       }); 

    // Erase the last ", " from the string, if present 
    if (result.size() > 0) { 
    result.erase(result.size() - 2, 2); 
    } 

    return result; 
} 

從本質上講,你必須循環在地圖中的每個元素,並將其添加到字符串。複雜度爲O(N)N地圖中元素的數量。

您可以改進算法在字符串結果上應用reserve的性能。

如果你知道字符串鍵的平均長度時,您可以初始化變量:

std::string result; 
result.reserve(map.size() * AVG_LENGTH_STR_KEY); 

這會提高很多循環中的operator+=操作。

1

作爲M.M.正確指出,你可以使用boost::range這個(我加入了boost::string)。

如果您的地圖是m,則

std::vector<std::string> o; 
boost::copy(m | boost::adaptors::map_keys, std::back_inserter(o)); 
boost::algorithm::join(o, ", "); 

最後一行是結果。 (不幸的是,這需要巨大的的頭文件。)

#include <boost/range/adaptor/map.hpp> 
#include <boost/range/algorithm/copy.hpp> 
#include <boost/assign.hpp> 
#include <boost/algorithm/string/join.hpp> 
#include <algorithm> 
#include <iostream> 
#include <map> 
#include <vector> 

int main() 
{ 
    std::map<std::string, std::string> m; 
    m["hello"] = "world"; 
    m["goodbye"] = "now"; 

    std::vector<std::string> o; 
    boost::copy(m | boost::adaptors::map_keys, std::back_inserter(o)); 
    std::cout << boost::algorithm::join(o, ", ") << std::endl; 
} 

此輸出

$ ./a.out 
goodbye, hello 
$ 
1

如果你不想使用升壓,然後嘗試std::accumulate

const std::string delimiter = "#"; 
const std::string result = std::accumulate(M.begin(), M.end(), std::string(), 
[delimiter](const std::string& s, const std::pair<const std::string, std::string>& p) { 
    return s + (s.empty() ? std::string() : delimiter) + p.first; 
}); 

在上面的代碼M是一個std::map<std::string, std::string>

+0

'M'的'value_type'是'pair '。注意額外的'const' – Barry

+0

@Barry很棒的評論!謝謝。固定。 –

相關問題