[hihoCoder] #1158 : 质数相关

时间限制:2000ms
单点时限:1000ms
内存限制:256MB

描述

两个数a和 b (a<b)被称为质数相关,是指a × p = b,这里p是一个质数。一个集合S被称为质数相关,是指S中存在两个质数相关的数,否则称S为质数无关。如{2, 8, 17}质数无关,但{2, 8, 16}, {3, 6}质数相关。现在给定一个集合S,问S的所有质数无关子集中,最大的子集的大小。

输入

第一行为一个数T,为数据组数。之后每组数据包含两行。

第一行为N,为集合S的大小。第二行为N个整数,表示集合内的数。

输出

对于每组数据输出一行,形如"Case #X: Y"。X为数据编号,从1开始,Y为最大的子集的大小。

数据范围

1 ≤ T ≤ 20

集合S内的数两两不同且范围在1到500000之间。

小数据

1 ≤ N ≤ 15

大数据

1 ≤ N ≤ 1000

样例输入
3

5

2 4 8 16 32

5

2 3 4 6 9

3

1 2 3

样例输出
Case #1: 3

Case #2: 3

Case #3: 2

编程之美2015初赛第一场第三题,找二分图的最大独立集,大小为:点的个数 - 最大匹配。

 1 #include <bits/stdc++.h>

 2 using namespace std;

 3 

 4 int T, N;

 5 vector<int> v;

 6 vector<vector<int>> graph;

 7 vector<int> link;

 8 vector<bool> visited;

 9 bool *isPrime;

10 

11 void getPrime() {

12     isPrime = new bool[500001];

13     memset(isPrime, true, sizeof(bool) * 500001);

14     isPrime[0] = isPrime[1] = false;

15     for (int i = 2; i * i < 500001; ++i) if (isPrime[i]) {

16         for (int j = 2; i * j < 500001; ++j) isPrime[i * j] = false;

17     }

18 }

19 

20 int dfs(int u) {

21     for (auto v : graph[u]) if (!visited[v]) {

22         visited[v] = true;

23         if (link[v] == -1 || dfs(link[v])) {

24             link[v] = u;

25             return 1;

26         }

27     }

28     return 0;

29 }

30 

31 int hungary() {

32     int res = 0;

33     for (int i = 0; i < N; ++i) {

34         visited.assign(N + 1, false);

35         res += dfs(i);

36     }

37     return res / 2;

38 }

39 

40 int main() {

41     getPrime();

42     cin >> T;

43     for (int t = 1; t <= T; ++t) {

44         cin >> N;

45         v.resize(N);

46         for (int i = 0; i < N; ++i) {

47             cin >> v[i];

48         }

49         sort(v.begin(), v.end());

50         graph.assign(N + 1, vector<int>());

51         link.assign(N + 1, -1);

52         for (int i = 0; i < N - 1; ++i) {

53             for (int j = i + 1; j < N; ++j) {

54                 if (v[j] % v[i] == 0) {

55                     int tmp = v[j] / v[i];

56                     if (isPrime[tmp]) {

57                         graph[i].push_back(j);

58                         graph[j].push_back(i);

59                     }

60                 }

61             }

62         }

63         cout << "Case #" << t << ": ";

64         int res = hungary();

65         cout << N - res << endl;

66     }

67     return 0;

68 }

 

你可能感兴趣的:(code)