UVA11754 - Code Feat

Hooray!  Agent Bauer has shot the terrorists, blown upthe bad guy base, saved the hostages, exposed the moles in the government,prevented an environmental catastrophe, and found homes for three orphanedkittens, all in the span of 19 consecutive hours.  But now, he only has 5 hours remaining todeal with his final challenge: an activated nuclear bomb protected by asecurity code.  Can you help him figureout the code and deactivate it?  Eventsoccur in real time.

The governmenthackers at CTU (Counter-Terrorist Unit) have learned some things about thecode, but they still haven‘t quite solved it.They know it‘s a single, strictly positive, integer.  They also know several clues of the form "whendivided by X, the remainder is one of {Y1, Y2, Y3, ...,Yk}".There are multiple solutions to these clues, but the code is likely tobe one of the smallest ones.  So they‘dlike you to print out the first few solutions, in increasing order.

The world iscounting on you!

Input

Input consistsof several test cases.  Each test casestarts with a line containing C, the number of clues (1 <= C <= 9), andS, the number of desired solutions (1 <= S <= 10).  The next C lines each start with two integersX (2 <= X) and k (1 <= k <= 100), followed by the k distinct integersY1, Y2, ..., Yk (0 <= Y1,Y2, ..., Yk < X).

You may assumethat the Xs in each test case are pairwise relativelyprime (ie, they have no common factor except 1).  Also, the product of the Xs will fit into a32-bit integer.

The last testcase is followed by a line containing two zeros.

Output

For each testcase, output S lines containing the S smallest positive solutions to the clues,in increasing order.

Print a blankline after the output for each test case.


Sample Input                              


Sample Output

 

3 2

2 1 1

5 2 0 3

3 2 1 2

0 0


5

13

 

思路:中国剩余定理+暴力;

首先我们肯定会想到dfs暴力枚举,这种情况只有当所有k的乘积很小的情况下才行,这个时候我们采取dfs+中国剩余定理;当k的乘积很大的情况下,

考虑选择一个K/X最小的条件,然后枚举所有符合这个条件的数n,即 tX+Yi ,t=0,1,2.... 然后依次判断这个n是否符合其它所有条件,因为这个时候x的增量很大。

  1 #include <cstdio>
  2 #include <iostream>
  3 #include <cstring>
  4 #include <algorithm>
  5 #include <map>
  6 #include <vector>
  7 #include <set>
  8 typedef long long LL;
  9 using namespace std;
 10 typedef struct node
 11 {
 12     int x;
 13     int y;
 14     int bns[105];
 15     double b;
 16 } ss;
 17 set<LL>ask;
 18 set<LL>::iterator it;
 19 set<int>val[20];
 20 ss ans[20];
 21 int a[20];
 22 void  dfs(int x,int y);
 23 LL china(int x);
 24 pair<LL,LL>ex_gcd(LL n,LL m);
 25 void slove__x(int n,int id,int m);
 26 LL R;
 27 bool cmp(node p,node q)
 28 {
 29     return p.b < q.b;
 30 }
 31 int main(void)
 32 {
 33     int n,m;
 34     while(scanf("%d %d",&n,&m)!=EOF)
 35     {
 36         if(n==0||m==0)break;
 37         int i,j;
 38         int id = 0;
 39         LL um = 1;
 40         for(i = 0; i < n; i++)
 41         {
 42             scanf("%d",&ans[i].x);
 43             scanf("%d",&ans[i].y);
 44             for(j = 0; j < ans[i].y; j++)
 45             {
 46                 scanf("%d",&ans[i].bns[j]);
 47             }
 48             sort(ans[i].bns,ans[i].bns+ans[i].y);
 49             if(ans[id].x*ans[i].y<ans[i].x*ans[id].y)id=i;
 50             um *= ans[i].y;
 51             ans[id].b = 1.0*ans[i].y/ans[i].x;
 52         }
 53         sort(ans,ans+n,cmp);
 54         if(um <= 10000)
 55         {
 56             ask.clear();
 57             R = 1;
 58             for(i = 0 ; i < n; i++)
 59             {
 60                 R *= ans[i].x;
 61             }
 62             dfs(0,n);
 63             int cn = 0;
 64             for(i = 0 ; m!=0; i++)
 65             {
 66                 for(it = ask.begin(); it!=ask.end(); it++)
 67                 {
 68                     LL tt = *it + i*R;
 69                     if(tt > 0)
 70                     {
 71                         m--;
 72                         printf("%lld\n",tt);
 73                         if(m==0)
 74                             break;
 75                     }
 76                 }
 77             }
 78         }
 79         else
 80         {
 81             slove__x(n,id,m);
 82         }
 83         printf("\n");
 84     }
 85     return 0;
 86 }
 87 void dfs(int x,int y)
 88 {
 89     if(x == y)
 90     {
 91         ask.insert(china(y));
 92         return ;
 93     }
 94     else for(int i = 0; i < ans[x].y; i++)
 95         {
 96             a[x] = ans[x].bns[i];
 97             dfs(x+1,y);
 98         }
 99 }
100 LL china(int x)
101 {
102     int i,j;
103     LL sum = 0;
104     LL ac = 1;
105     ac = R;
106     for(i = 0; i < x; i++)
107     {
108         LL ak = ac/ans[i].x;
109         pair<LL,LL>cc = ex_gcd(ak,ans[i].x);
110         LL aa = cc.first;
111         aa = (aa%ans[i].x + ans[i].x)%ans[i].x;
112         sum = sum + ((aa*ak%ac)*a[i])%ac;
113         sum %= ac;
114         sum += ac;
115         sum %= ac;
116     }
117     return sum;
118 }
119 pair<LL,LL>ex_gcd(LL n,LL m)
120 {
121     if(m == 0)
122         return make_pair(1,0);
123     else
124     {
125         pair<LL,LL>ac = ex_gcd(m,n%m);
126         return make_pair(ac.second,ac.first-(n/m)*ac.second);
127     }
128 }
129 void slove__x(int n,int id,int m)
130 {
131     int i,j;
132     for(i = 0; i < n; i++)
133         val[i].clear();
134     for(i = 0; i < n; i++)
135     {
136         for(j = 0; j < ans[i].y; j++)
137         {
138             val[i].insert(ans[i].bns[j]);
139         }
140     }
141     for(i = 0; m != 0; i++)
142     {
143         for(j = 0; j < ans[id].y; j++)
144         {
145             LL ak = (LL)i*(LL)ans[id].x + ans[id].bns[j];
146             if(ak > 0)
147             {
148                 int flag = 0;
149                 for(int c = 0; c < n; c++)
150                 {
151                     if(c!=id)
152                     {
153                         if(!val[c].count(ak%ans[c].x))
154                         {
155                             flag = 1;
156                             break;
157                         }
158                     }
159                 }
160                 if(!flag)
161                 {
162                     printf("%lld\n",ak);
163                     m--;
164                 }
165                 if(m==0)break;
166             }
167         }
168     }
169 }
时间: 2024-08-10 21:22:53

UVA11754 - Code Feat的相关文章

UVA 11754 Code Feat (枚举,中国剩余定理)

转载请注明出处: http://www.cnblogs.com/fraud/          ——by fraud C Code Feat   The government hackers at CTU (Counter-Terrorist Unit) have learned some things about the code, but they still haven't quite solved it.They know it's a single, strictly positive

UVA 11754 - Code Feat(数论)

UVA 11754 - Code Feat 题目链接 题意:给定一个c个x, y1,y2,y3..yk形式,前s小的答案满足s % x在集合y1, y2, y3 ... yk中 思路:LRJ大白例题,分两种情况讨论 1.所有x之积较小时候,暴力枚举每个集合选哪个y,然后中国剩余定理求解 2.所有x之积较大时候,选定一个k/x尽可能小的序列,枚举x * t + y (t = 1, 2, 3...)去暴力求解. 代码: #include <stdio.h> #include <string.

uva 11754 - Code Feat(中国剩余定理+暴力)

题目链接:uva 11754 - Code Feat 题目大意:求一个数N,给出C和S,表示有C个条件,每个条件有X 和 k,然后是该个条件的k个yi,即NmodX=yj,输出满足的最小的S个N,要求正整数. 解题思路:total为所有的k的乘积,也就是可以作为一组完整限定条件的可能数,当个确定条件可以用中国剩余定理处理.但是如果total太大的话,处理的情况比较多.不过total数大的时候,可以通过枚举N来判断,找到一组k/x最小的最为枚举基准,然后判断即可. #include <cstdio

Uva 11754 Code Feat

题意概述: 有一个正整数$N$满足$C$个条件,每个条件都形如“它除以$X$的余数在集合$\{Y_1, Y_2, ..., Y_k\}$中”,所有条件中的$X$两两互质, 你的任务是找出最小的S个解. 数据范围: $1\leq C\leq9, 1 \leq S \leq 10, X \geq 2, 1 \leq k \leq 100, 0 \leq Y_i \leq X$ 分析: 如果每个集合元素个数为1,那么我们直接使用中国剩余定理求解即可. 因此我们想到枚举余数,但是余数的组合最多会有$10

UVa 11754 (中国剩余定理 枚举) Code Feat

如果直接枚举的话,枚举量为k1 * k2 *...* kc 根据枚举量的不同,有两种解法. 枚举量不是太大的话,比如不超过1e4,可以枚举每个集合中的余数Yi,然后用中国剩余定理求解.解的个数不够S个的时候,要把这些解分别加上M.2M...(M = X1 * X2 *...* Xc) 如果上述枚举量太大的话,直接枚举x.找一个k/X最小的条件,然后让x = t * X + Yi开始枚举,因为这样枚举x增长得最快,所以枚举次数也就最少.如果符合要求的话则输出. 上面两种方法都要注意所找到的解为正整

UVA - 11754 Code Feat (分块+中国剩余定理)

对于一个正整数N,给出C组限制条件,每组限制条件为N%X[i]∈{Y1,Y2,Y3,...,Yk[i]},求满足条件的前S小的N. 这道题很容易想到用中国剩余定理,然后用求第k小集合的方法输出答案.但是一取模,孰大孰小就不好控制了,所以行不通.直接枚举所有情况的话,总方案数(所有k的乘积)高达C*k,显然也是不行的. 还有一种方法是枚举所有可能的N,然后检验是否满足条件.对于每个满足条件的N,任取某个限制条件i,对于其中某个余数j,都可以写成X[i]*t+Y[i][j]的形式.复杂度未知,但总方

《算法竞赛入门经典——训练指南》第二章题库

UVa特别题库 UVa网站专门为本书设立的分类题库配合,方便读者提交: http://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&category=442 注意,下面注有"extra"的习题并没有在书中出现,但在上面的特别题库中有,属于附加习题. 基础练习 (Basic Problems) UVa11388 GCD LCM UVa11889 Benefit UVa10943 How do y

ios code style

注释 建议使用VVDocumenter插件 多行注释 格式: /** 注释内容 */ 单行注释 格式: ///在对文件.类.函数进行注释时推荐使用多行注释,在函数体内对代码块进行注释时,使用单行注释 函数的注释 函数注释的格式为 /** * @brief * @param * @return **/ 在brief中需要写明函数的主要功能.注意事项 在param中需要写明函数的变量类型.变量的作用 在return中需要写明函数的返回类型.返回值的作用 如有其他需要说明的地方,可以在@return后

Position Independent Code (PIC) in shared libraries【转载】

I've described the need for special handling of shared libraries while loading them into the process's address space in a previous article. Briefly, when the linker creates a shared library, it doesn't know in advance where it might be loaded. This c