2013-02-27 61 views
1

如何遍歷C++中的部分地圖?我的最終目標是讓多個線程遍歷地圖的一部分並計算一些值。該地圖的類型爲std::map<std::string, std::vector<double> >在C++中迭代部分地圖

+0

怎麼樣'的std :: for_each的()'? – 2013-02-27 00:09:15

+2

你想要迭代哪部分地圖?是的,它可以完成,是的,我知道如何。但除非我知道如何選擇地圖的一部分進行迭代的準則,否則我不能告訴你如何去做。 – jalf 2013-02-27 00:10:33

+0

@jalf:所以如果我有4個線程,那麼每個線程將通過地圖尺寸的四分之一 – 2013-02-27 00:14:10

回答

2

這裏是做C++ 11的一個簡單的方法:

#include <map> 
#include <string> 
#include <vector> 
#include <algorithm> 
#include <future> 
#include <iostream> 

typedef std::map<std::string, std::vector<double>> map_type; 

void do_work(map_type::iterator b, map_type::iterator e) 
{ 
    std::for_each(b, e, [] (map_type::value_type const& p) 
    { 
     std::for_each(p.second.begin(), p.second.end(), [] (double d) 
     { 
      /* Process an element of the vector... */ 
     }); 
    }); 
} 

int main() 
{ 
    map_type m; 

    size_t s = m.size(); 
    int quarter = s/4; 
    auto i1 = m.begin(); 
    auto i2 = std::next(i1, quarter); 
    auto i3 = std::next(i2, quarter); 
    auto i4 = std::next(i3, quarter); 
    auto i5 = m.end(); 

    std::vector<std::future<void>> futures; 
    futures.push_back(std::async(do_work, i1, i2)); 
    futures.push_back(std::async(do_work, i2, i3)); 
    futures.push_back(std::async(do_work, i3, i4)); 
    futures.push_back(std::async(do_work, i4, i5)); 

    for (auto& f : futures) { f.wait(); } 
} 
+1

嗯,我有一個想法,如何templatize,並創建阿爾戈稱爲像parallel_foreach? – Slava 2013-02-27 00:32:00

+0

@Slava:我很確定已經存在 – 2013-02-27 00:32:32

+1

爲什麼總是這樣:當你有一個好主意時,其他人已經實現了這個目標? – Slava 2013-02-27 00:36:21

1

如果您希望均勻分割工作,則映射可能不是最佳數據結構。你需要遍歷map並找到特定位置的迭代器。如果你使用提供隨機訪問迭代器的容器,比如std :: vector,那麼你可以用算術計算迭代器。 如果你想這樣做的字母順序,那麼你可以做這樣的事情:

typedef std::map<std::string,std::vector<double>> data; 

void process(data::iterator beg, data::iterator end); 
data dt; 
{ 
    auto task1 = std::async(process, dt.begin(), dt.lower_bound("n")); 
    auto task2 = std::async(process, dt.lower_bound("n"), dt.end()); 
} 

假設所有字符串都是小寫。