合并C 中的两个增强侵入性集

Merge two boost intrusive sets in C++?

本文关键字:增强 两个 合并      更新时间:2023-10-16

我有两个提升侵入式集合,我需要将其合并在一起。我有map_old.m_old_attributes提升侵入式套件,我需要将其合并到m_map_new_attributes增强intruse Set

void DataTest::merge_set(DataMap& map_old)
{
    // merge map_old.m_old_attributes set into m_map_new_attributes
}

最好的方法是什么?我找不到可以为我合并的函数吗?我最近开始使用Boost Intruse套装,但我找不到可以合并的预定义方法,或者我可能错了?

确实是侵入性的集合是另一种野兽。他们不管理元素分配。

因此,当合并时,您需要决定的含义。我想说一个合理的解释是,您要移动移动 map_old容器内包含的元素进入数据amap。

这将使map_old空。这是这样的算法:

template <typename Set>
void merge_into(Set& s, Set& into) {
    std::vector<std::reference_wrapper<Element> > tmp(s.begin(), s.end());
    s.clear(); // important! unlinks the existing hooks
    into.insert(tmp.begin(), tmp.end());
}

更新另外您可以使用略带棘手的iterater-erase-loop(当心迭代突变容器): live live live

    for (auto it = s.begin(); it != s.end();) {
        auto& e = *it;
        it = s.erase(it);
        into.insert(e);
    }

请参阅 Live on Coliru

#include <boost/intrusive/set.hpp>
#include <boost/intrusive/set_hook.hpp>
#include <string>
#include <vector>
#include <functional>
#include <iostream>
namespace bive = boost::intrusive;
struct Element : bive::set_base_hook<> {
    std::string data;
    Element(std::string const& data = "") : data(data) {}
    bool operator< (Element const& rhs) const  { return data < rhs.data; }
    bool operator==(Element const& rhs) const  { return data ==rhs.data; }
};
using Set = bive::set<Element>;
template <typename Set>
void merge_into(Set& s, Set& into) {
    std::vector<std::reference_wrapper<Element> > tmp(s.begin(), s.end());
    s.clear(); // important! unlinks the existing hooks
    into.insert(tmp.begin(), tmp.end());
}
int main() {
    std::vector<Element> va {{"one"},{"two"},{"three"},{"four"},{"five"},{"six"},{"seven"},{"eight"},{"nine"} };
    Set a;
    for(auto& v : va) a.insert(v);
    std::vector<Element> vb {{"two"},{"four"},{"six"},{"eight"},{"ten"} };
    Set b;
    for(auto& v : vb) b.insert(v);
    assert(9==a.size());
    assert(5==b.size());
    merge_into(a, b);
    assert(a.empty());
    assert(10==b.size());
}

当然,您可以为合并操作提出不同的语义(这更类似于"复制"而不是"移动")