2015 programming-related to the first C-quality game in the US preliminary round, and the first game in 2015
Time limit: 256 ms single point time limit: Ms memory limit: MB
Description
Two numbers a and B (a <B) are called prime number correlation, which means a × p = B. Here p is a prime number. A set of S is called prime number correlation. It refers to the number of two prime numbers in S. Otherwise, it is called prime number. For example, {2, 8, 17} is irrelevant, but {2, 8, 16}, {3, 6} is related. Given a set of S, the size of the largest subset of all prime numbers in S is not correlated.
Input
The first act is a number T, which is the number of data groups. Each group contains two rows.
The first behavior N is the size of the Set S. The second act is an integer of N, indicating the number in the set.
Output
Output a row of data in each group, such as "Case # X: Y ". X indicates the data number. Starting from 1, Y indicates the size of the largest subset.
Data range
1 ≤ T ≤ 20
The numbers in the Set S are two or two different and the range is between 1 and 500000.
Small Data
1 ≤ N ≤ 15
Big Data
1 ≤ N ≤1000
-
Sample Input
-
352 4 8 16 3252 3 4 6 931 2 3
-
Sample output
-
Case #1: 3Case #2: 3Case #3: 2
2. Solutions: Use the largest stream to solve the problem. First, we can find all the numbers related to the prime numbers. Here we use the ss array to mark them. Next is the graph creation process. If the number a [I] is correlated with the prime number, an edge is connected between I and the Source Vertex s. Otherwise, an edge is connected to the vertex t. Next, if you find the number a [I] = a [j] * p, or a [j] = a [I] * p, connect an edge between I and j. The capacity of all edges is 1. Next we will solve the maximum flow for this graph. Based on the maximum flow theorem of the minimum cut, we can see that n-maxflow () is the subset with the largest number of irrelevant points.
3. Code:
# Define _ CRT_SECURE_NO_WARNINGS # include <iostream> # include <algorithm> # include <string> # include <sstream> # include <set> # include <vector> # include <stack> # include <map> # include <queue> # include <deque> # include <cstdlib> # include <cstdio> # include <cstring> # include <cmath> # include <ctime> # include <functional> using namespace std; int ss [510000], T, a [1100]; bool prime [510000]; # define INF 1000000000 # define min (x, y) (x) <(Y )? (X): (y) int n, m, I, q, h, mid, len, s, t, till [3100000], go [3100000], next [3100000], f [3100000], D [3100000], n1 [3100000]; bool cc [3100000]; void add (int x, int y, int z) {Next [++ len] = till [x]; till [x] = len; go [len] = y; f [len] = z ;} void Ad (int x, int y, int z) {add (x, y, z); add (y, x, 0);} bool bfs () {int q, h, I; memset (D, 0, sizeof D); memset (cc, 1, sizeof cc ); for (D [n1 [q = h = 1] = s] = 1; q <= h; Q ++) for (I = till [n1 [q]; I = Next [I]) if (f [I] &! D [go [I]) D [n1 [++ h] = go [I] = D [n1 [q] + 1; return D [t];} int dfs (int k, int mi) {if (k = t) return mi; int I, tmp, sum = 0; for (I = till [k]; I & mi; I = Next [I]) if (f [I] & D [go [I] = D [k] + 1 & cc [go [I]) {tmp = dfs (go [I], min (mi, f [I]); sum + = tmp; mi-= tmp; f [I]-= tmp; f [I ^ 1] + = tmp;} if (! Sum) cc [k] = false; return sum;} int maxFlow () {int sum = 0; while (bfs () sum + = dfs (s, INF ); return sum;} int main () {freopen ("t.txt", "r", stdin); ss [1] = 0; for (int I = 2; I <= 500000; I ++) // sieve prime number prime [I] = true; for (int I = 2; I <= 500000; I ++) {for (int j = I + I; j <= 500000; j + = I) prime [j] = false;} for (int I = 1; I <= 500000; I ++) for (int j = 1; j <= 500000/I; j ++) if (prime [j]) ss [I * j] = 1-s S [I]; // mark the numbers related to all prime numbers as 1 scanf ("% d", & T); for (int mm = 1; mm <= T; mm ++) {printf ("Case # % d:", mm); scanf ("% d", & n); for (int I = 1; I <= n; I ++) scanf ("% d", & a [I]); len = 1; s = 0; // source point t = n + 1; // sink point for (int I = 0; I <= n + 1; I ++) till [I] = 0; for (int I = 1; I <= n; I ++) if (ss [a [I]) Ad (0, I, 1); // if a [I] is a prime number, the Source Vertex and I are connected to an edge else Ad (I, n + 1, 1); // otherwise, I and the sink vertex are connected to for (int I = 1; I <= n; I ++) if (ss [a [I]) for (int j = 1; J <= n; j ++) if (! Ss [a [j]) {if (a [I]> a [j]) {if (a [I] % a [j] = 0 & prime [a [I]/a [j]) Ad (I, j, 1 ); // If a [I] is correlated with the prime number and the prime number is a [I]/a [j], connecting an edge between I and j} else {if (a [j] % a [I] = 0 & prime [a [j]/a [I]) ad (I, j, 1) ;}} printf ("% d \ n", n-maxFlow (); // use the Dinic algorithm to find the maximum stream, by using the maximum flow theorem of the smallest cut, the remaining vertex is the largest subset }}