【发布时间】:2020-05-17 08:51:39
【问题描述】:
我无法从文档中推断我可以使用std::set_difference,因为它说集合应该是有序的,这意味着它们不是集合,而是列表。此外,所有示例都是关于有序列表,而不是集合。
如何知道真相?
【问题讨论】:
标签: c++ set set-difference
我无法从文档中推断我可以使用std::set_difference,因为它说集合应该是有序的,这意味着它们不是集合,而是列表。此外,所有示例都是关于有序列表,而不是集合。
如何知道真相?
【问题讨论】:
标签: c++ set set-difference
std::set_difference 用于任意排序的输入(预排序的std::vectors、std::lists、std::deques、普通数组等),它恰好适用于std::set(其中也已排序)。
如果您正在使用std::unordered_set(或std::set,并且您可以就地操作),您只需使用erase 方法从一个这样的集合中删除所有元素到另一个获取差异,例如:
for (const auto& elem : set_to_remove) {
myset.erase(elem);
}
你也可以把它做成一个新的集合with std::copy_if;那里的配方非常适用于对称差异的情况(它只是对std::copy_if 的两次调用,其中每个调用在一个输入集上运行,并且以其他输入集中不存在的元素为条件)。
【讨论】:
std::set::erase 的这种用法仅适用于 属于 myset 的迭代器。参见here:“删除[first; last) 范围内的元素,该范围必须是*this 中的有效范围。”
set_to_remove 并使用erase 的按值版本的版本替换了坏代码。感谢您接听!
std::set 已排序。查看docs:
std::set 是一个关联容器,其中包含 一个排序集 Key 类型的唯一对象。排序是使用键比较完成的 功能比较。搜索、删除和插入操作 对数复杂度。集合通常实现为红黑 树。
因此,您可以像使用任何其他提供所需接口的容器一样使用它。 std::set 和 e.g. 之间的区别std::vector 是 std::set 在插入时对其元素进行排序,如果是 std::vector,您需要使用 std::sort 函数对其元素进行排序。
例如,如果您需要std::set_difference 为std::unordered_set,您可以这样做:
#include <set>
#include <iostream>
#include <algorithm>
#include <unordered_set>
int main() {
std::unordered_set<int> a {3, 1, 4, 6, 5, 9};
std::unordered_set<int> b {3, 1, 4};
std::set<int> c;
std::set<int> d;
std::copy(a.begin(), a.end(), std::inserter(c, c.end()));
std::copy(b.begin(), b.end(), std::inserter(d, d.end()));
std::vector<int> diff;
std::set_difference(c.begin(), c.end(), d.begin(), d.end(),
std::inserter(diff, diff.begin()));
for (auto const i : diff)
std::cout << i << ' ';
return 0;
}
见live
【讨论】: