2014-03-06 53 views
1

我正在嘗試爲我的一個需求使用boost :: bimap。下面的示例代碼來自boost :: bimap的各種值之間的交集

typedef bimap< 
     multiset_of<string>, 
     multiset_of<string>, 
     set_of_relation<> 
     > bm_type; 

bm_type bm; 

assign::insert(bm) 

("John" , string("lazarus")) 
("Peter", string("vinicius")) 
("Peter", string("test")) 
("Simon", string("vinicius")) 
("John", string("viniciusa")) 
("John", string("vinicius")) 

我想約翰&彼得做一些事情,作爲約翰·&彼得找到匹配值,在值之間換句話說交集例如:在這種情況下,這將是(「維尼」) 。有人可以提供一些關注它的風頭嗎?

回答

2

這就是我想出了最初:

template <typename Value = std::string, typename Bimap, typename Key> 
std::set<Value> projection(Bimap const& bm, Key const& key) 
{ 
    std::set<Value> p; 
    auto range = bm.left.equal_range(key); 
    auto values = boost::make_iterator_range(range.first, range.second); 

    for (auto& relation : values) 
     p.insert(relation.template get<boost::bimaps::member_at::right>()); 

    return p; 
} 

auto john = projection(bm, "John"); 
auto peter = projection(bm, "Peter"); 

std::multiset<std::string> intersection; 
std::set_intersection(
     john.begin(), john.end(), 
     peter.begin(), peter.end(), 
     inserter(intersection, intersection.end()) 
    ); 

我認爲它可以更有效率。所以,我想更換使用提升的限定範圍的適配器飛投影:

struct GetRightMember 
{ 
    template <typename> struct result { typedef std::string type; }; 

    template <typename T> 
    std::string operator()(T const& v) const { 
     return v.template get<boost::bimaps::member_at::right>(); 
    } 
}; 

const GetRightMember getright; 
std::cout << "Intersection: "; 

// WARNING: broken: ranges not sorted 
boost::set_intersection(
     bm.left.equal_range("John") | transformed(getright), 
     bm.left.equal_range("Peter") | transformed(getright), 
     std::ostream_iterator<std::string>(std::cout, " ")); 

可悲的不起作用 - 大概是因爲改造範圍進行排序。

所以我會堅持更詳細的版本(或重新考慮我的數據結構選擇)。看到它Live On Coliru

+0

如果我使用unordered_multiset_of的bimap,甚至可以工作嗎? – Blackhole

+0

我強烈期待這一點。你有沒有嘗試過? **更新** 59秒後:http://coliru.stacked-crooked.com/a/69e331d13cef1c65 – sehe

+0

我可以通過使用unordered_map <字符串,設置(鍵值2的一組值)&另一個unordered_map < string,unordered_set >(value to 2 unordered_set of keys)。在那種情況下,我需要管理從第一張地圖中刪除,如果有東西在第二和反之亦然(當然也是相同的添加以及),但這種方式,我不需要創建組來找到不同的鍵之間的交集,你認爲這比使用bimap更有效率? – Blackhole