文先生的博客 求职,坐标深圳。(wenfh2020@126.com)

计算两个集合差集(C++)

2020-11-01

标准库里有这个函数:set_difference,它可以计算两个集合的差集。

它的算法实现并不复杂,但是要求传进来的两个参数数组集合数据都是有序的(从小到大排列)。

cppreference.com 有详细文档和测试用例。


1. 源码

我封装了一个比较通用的模板函数 diff_cmp:

1
2
3
4
5
6
7
8
9
10
11
12
template <typename T>
std::vector<T> diff_cmp(std::vector<T>& first, std::vector<T>& second) {
    std::vector<T> diff;
    /* 排序 */
    std::sort(first.begin(), first.end(), std::less<T>());
    std::sort(second.begin(), second.end(), std::less<T>());
    /* 求两个集合差集 */
    std::set_difference(first.begin(), first.end(), second.begin(),
                        second.end(), std::inserter(diff, diff.begin()));
    /* 返回差集结果。*/
    return diff;
}

2. 测试

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
#include <algorithm>
#include <iostream>
#include <vector>

/* 求差集数组模板。 */
template <typename T>
std::vector<T> diff_cmp(std::vector<T>& first, std::vector<T>& second) {
    std::vector<T> diff;
    /* 排序 */
    std::sort(first.begin(), first.end(), std::less<T>());
    std::sort(second.begin(), second.end(), std::less<T>());
    /* 求两个集合差集 */
    std::set_difference(first.begin(), first.end(), second.begin(),
                        second.end(), std::inserter(diff, diff.begin()));
    return diff;
}

void diff_int() {
    ...
    std::vector<int> diff;
    std::vector<int> first{9, 2, 3, 7, 5, 4, 1};
    std::vector<int> second{10, 2, 8, 5, 6, 3, 1};
    ...
    diff = diff_cmp(first, second);
    ...
    diff = diff_cmp(second, first);
    ...
}

void diff_string(bool turn = false) {
    ...
    std::vector<std::string> diff;
    std::vector<std::string> first{"192.168.0.1:1122.1", "192.168.0.1:1122.3", "192.168.0.1:1133.1", "192.168.0.1:1133.2"};
    std::vector<std::string> second{"192.168.0.1:1122.1", "192.168.0.1:1122.2", "192.168.0.1:1133.1", "192.168.0.1:1133.3"};
    ...
    diff = diff_cmp(first, second);
    ...
    diff = diff_cmp(second, first);
    ...
}

int main() {
    diff_int();
    diff_string();
}
  • 测试结果。
1
2
3
4
5
6
7
8
9
10
-------
first: 9, 2, 3, 7, 5, 4, 1,
second: 10, 2, 8, 5, 6, 3, 1,
turn: 0, diff: 4, 7, 9,
turn: 1, diff: 6, 8, 10,
-------
first: 192.168.0.1:1122.1, 192.168.0.1:1122.3, 192.168.0.1:1133.1, 192.168.0.1:1133.2,
second: 192.168.0.1:1122.1, 192.168.0.1:1122.2, 192.168.0.1:1133.1, 192.168.0.1:1133.3,
turn: 0, diff: 192.168.0.1:1122.3, 192.168.0.1:1133.2,
turn: 1, diff: 192.168.0.1:1122.2, 192.168.0.1:1133.3,

3. 参考


作者公众号
微信公众号,干货持续更新~