Game with Pearls
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/65536 K (Java/Others)
Total Submission(s): 646 Accepted Submission(s): 284
Problem Description
Tom and Jerry are playing a game with tubes and pearls. The rule of the game is:
1) Tom and Jerry come up together with a number K.
2) Tom provides N tubes. Within each tube, there are several pearls. The number of pearls in each tube is at least 1 and at most N.
3) Jerry puts some more pearls into each tube. The number of pearls put into each tube has to be either 0 or a positive multiple of K. After that Jerry organizes these tubes in the order that the first tube has exact one pearl, the 2nd tube has exact 2 pearls, …, the Nth tube has exact N pearls.
4) If Jerry succeeds, he wins the game, otherwise Tom wins.
Write a program to determine who wins the game according to a given N, K and initial number of pearls in each tube. If Tom wins the game, output “Tom”, otherwise, output “Jerry”.
Input
The first line contains an integer M (M<=500), then M games follow. For each game, the first line contains 2 integers, N and K (1 <= N <= 100, 1 <= K <= N), and the second line contains N integers presenting the number of pearls in each tube.
Output
For each game, output a line containing either “Tom” or “Jerry”.
Sample Input
2
5 1
1 2 3 4 5
6 2
1 2 3 4 5 5
Sample Output
Jerry
Tom
Source
题目意思:
给一序列,序列每个数字可以加上0个或多个k,若这个序列能形成每个i有a[i]==i,输出jerry,否则输出tom。
思路:
原序列中若a变成c,那么b就不能变成c了,这样就满足二分匹配了。a可以变成a+j*k(j>=0&&j<=n) ,a和a+j*k连边建图求二分最大匹配,若匹配数ans==n输出jerry,否则输出tom。
代码:
1 #include <cstdio> 2 #include <cstring> 3 #include <algorithm> 4 #include <iostream> 5 #include <vector> 6 #include <queue> 7 using namespace std; 8 9 #define N 105 10 11 int max(int x,int y){return x>y?x:y;} 12 int min(int x,int y){return x<y?x:y;} 13 int abs(int x,int y){return x<0?-x:x;} 14 15 int a[N]; 16 int n, m, k; 17 int from[N]; 18 bool visited[N]; 19 vector<int>ve[N]; 20 21 int march(int u){ 22 int i, v; 23 for(i=0;i<ve[u].size();i++){ 24 v=ve[u][i]; 25 if(!visited[v]){ 26 visited[v]=true; 27 if(from[v]==-1||march(from[v])){ 28 from[v]=u; 29 return 1; 30 } 31 } 32 } 33 return 0; 34 } 35 36 main() 37 { 38 int i, j; 39 cin>>m; 40 while(m--){ 41 scanf("%d %d",&n,&k); 42 for(i=1;i<=n;i++) scanf("%d",&a[i]); 43 for(i=0;i<=n;i++) ve[i].clear(); 44 bool flag; 45 for(i=1;i<=n;i++){ 46 flag=false; 47 for(j=0;j<=i;j++){ 48 if(a[i]+j*k<=n&&(a[i]+j*k)) { 49 ve[i].push_back(a[i]+j*k); 50 } 51 else break; 52 } 53 } 54 55 memset(from,-1,sizeof(from)); 56 int ans=0; 57 for(i=1;i<=n;i++){ 58 memset(visited,false,sizeof(visited)); 59 if(march(i)) ans++; 60 } 61 if(ans!=n) printf("Tom\n"); 62 else printf("Jerry\n"); 63 } 64 }