C ++ - 将一个Vector附加到另一个,删除重复项?

时间:2011-04-03 10:36:13

标签: c++ vector

我想将一个向量(vectorAlpha)附加到另一个向量(vectorBeta)的末尾。我能想到两种不同的方法,我想知道如何做每一种方法。

第一种方法是追加第二个向量并从新向量中删除所有重复项。另一种方法是单独在单个向量中留下重复项,但如果它们已经存在于vectorALpha中,则不会添加来自vectorBeta的任何项。

例如,如果向量是具有以下值的向量:

vectorAlpha:

First line of alpha
An alpha line
An alpha line
Some line
Alpha fifth line

vectorBeta:

Beta first line
A beta line
A beta line
Some line
Beta fifth line

我认为第一种方法会产生组合向量:

First line of alpha
An alpha line
Some line
Alpha fifth line
Beta first line
A beta line
Beta fifth line

虽然第二种方法只是两个数组合并,但第二个向量中的'Some line'没有添加:

First line of alpha
An alpha line
An alpha line
Some line
Alpha fifth line
Beta first line
A beta line
A beta line
Beta fifth line

用于这两个appraoches的C ++代码是什么?

3 个答案:

答案 0 :(得分:5)

因为很明显

  1. 你只想要重复删除vecB中的条目(如果它们存在于vecA中,而不是一般的重复项
  2. 您想保留订购
  3. 答案应该(显然是?)是std :: remove_copy_if。这么称呼它:

    #include <vector>
    #include <algorithm>
    
    typedef std::vector<int> Vec;
    struct Contained
    {
        const Vec& _sequence;
        Contained(const Vec &vec) : _sequence(vec) {}
        bool operator()(int i) const 
        { 
            return _sequence.end() != std::find(_sequence.begin(), _sequence.end(), i);
        }
    };
    
    int main()
    {
        Vec vecA;
        Vec vecB;
    
        std::remove_copy_if(vecB.begin(), vecB.end(), back_inserter(vecA), Contained(vecA));
    }
    

    您可能希望根据vecA的大小和性质优化谓词:

    #include <set>
    
    template <typename T>
    struct Contained
    {
        const std::set<T> _set;
        template <typename It> Contained(const It& begin, const It& end) : _set(begin, end) {}
        bool operator()(const T& i) const 
        { 
            return _set.end() != _set.find(i);
        }
    };
    

    将用作Contained<int>(vecA.begin(), vecA.end())。完整代码is compiling on codepad.org

    干杯

答案 1 :(得分:4)

更新:新answer here due to changed/added requirements

typedef std::...<...> Vec;
Vec vecA;
Vec vecB;

// fill your data

// sort
std::sort(vecA.begin(), vecA.end());
std::sort(vecA.begin(), vecA.end());


// join
Vec::iterator mergepoint = vecA.end();

std::copy(vecB.begin(), vecB.end(), std::back_inserter(vecA));

// merge
std::inplace_merge(vecA.begin(), mergepoint, vecA.end());

您可以将加入+合并步骤组合如下

Vec vecC;
std::merge(vecA.begin(), vecA.end(),
            vecB.begin(), vecB.end(),
            std::back_insterter(vecC));

最后一步,删除重复项:

Vec::iterator pte = std::unique(vecC.begin(), vecC.end());
// dups now in [pte, vecC.end()), so optionally erase:
vecC.erase(pte, vecC.end());

答案 2 :(得分:3)

两个向量中元素的顺序是否重要?如果没有,那么你可能应该使用集合。