【问题标题】:Remove duplicates in two vector based on duplicates on first vector根据第一个向量上的重复项删除两个向量中的重复项
【发布时间】:2020-08-03 14:16:42
【问题描述】:

我有两个相关的向量。向量具有相同的大小,并且它们的内容匹配 1:1,因为它可以被重构为某个结构的单个向量。我正在尝试删除第一个向量上的重复项,这应该与第二个向量匹配。

v1 = [5 4 3 7 6 5 2 3]
v2 = [0 1 2 3 4 5 6 7]

由于v1中重复了5和3,所以结果应该是

v1 = [5 4 3 7 6 2]
v2 = [0 1 2 3 4 6]

顺序可以更改,只要关系相同即可。

我正在尝试使用 range-v3 库来实现这一点。

std::vector<unsigned int>  v1;
std::vector<double> v2;

auto v1Andv2 = range::views::zip(v1, v2);
ranges::sort(v1Andv2)
// ranges::unique(v1Andv2) // Doesnt compile
auto lastIt = std::unique(std::begin(v1Andv2), std::end(v1Andv2), [](const auto &a, const auto &b) {
    // Since the second value of the zip is a double and could be slightly different, 
    // I am only interested in first one
    return std::get<0>(a) == std::get<0>(b);
});

v1.erase(???, std::end(v1));
v2.erase(???, std::end(v2));

我不知道我应该在 ???获取 zip 中的每个值的迭代器。 另外,为什么 range::actions::unique 在这种情况下不起作用?

【问题讨论】:

    标签: c++ range-v3


    【解决方案1】:

    您遇到的问题是您不能sort 或以其他方式修改view。如果你只是创建一个对的向量,那么你可以毫无问题地使用sortunique

    auto vv = ranges::views::zip(v1, v2) | 
              ranges::to<std::vector<std::pair<int,int>>>;
    
    vv |= ranges::actions::sort([](auto const &a, auto const &b)
                                { return a.first < b.first; })
        | ranges::actions::unique([](auto const &a, auto const &b)
                                  { return a.first == b.first; });
    

    这是一个有效的demo

    您甚至可以再次通过sorting 将其重新排列为原始顺序,如下所示:

    vv |= ranges::actions::sort([](auto const &a, auto const &b)
                                { return a.first < b.first; })
       | ranges::actions::unique([](auto const &a, auto const &b)
                                 { return a.first == b.first; })
       | ranges::actions::sort([](auto const &a, auto const &b)
                               { return a.second < b.second; });
    

    这是demo

    【讨论】:

    • 使用 boost::zip_iterator 这个(排序 + 唯一)应该可以开箱即用,而不需要创建中间容器,不是吗?
    • 我不确定 boost 是如何做到这一点的,但通常视图不会存储在内存中,您需要将元素放在内存中才能进行排序。
    • 这让我很困惑。如果您考虑使用迭代器,则可以有一对迭代器,每个容器一个,并执行与第一个迭代器到第二个迭代器相同的操作。我本来希望 zip 可以这样工作
    • 我不是 100% 确定,但我刚刚试用了你的版本,至少 range-v3 不能这样工作。
    • 所以你有测试对视图范围进行排序并且它产生错误的结果?这很奇怪,它在这里产生了很好的效果:-s
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-09-16
    • 2020-04-29
    • 2011-11-29
    • 2022-01-20
    相关资源
    最近更新 更多