50 条题解
-
3Fop_zz LV 10 @ 2017-06-06 08:10:50
这不是个BFS嘛。。一脸懵逼
先对输入的数字排序,就可以保证先生成出0的那个数字一定最小
最多5000种状态。。BFS秒过#include <iostream> #include <cstdio> #include <cmath> #include <algorithm> #include <queue> #include <string> #include <map> #include <cstring> #include <ctime> #include <vector> #define inf 1e9 #define ll long long #define For(i,j,k) for(int i=j;i<=k;i++) #define Dow(i,j,k) for(int i=k;i>=j;i--) using namespace std; int n,m,a[101],q[10001],num[10001],nxt[10001],vis[10001],l=1,r,ans,tot,ANS[10001]; int main() { scanf("%d%d",&n,&m); For(i,1,m) scanf("%d",&a[i]); sort(a+1,a+m+1); For(i,1,m) if(a[i]&&!vis[a[i]%n]) q[++r]=a[i]%n,vis[a[i]%n]=1,num[r]=a[i],nxt[r]=-1; while(l<=r) { int t=q[l]; if(t==0){ans=l;break;} For(i,1,m) { int tmp=(t*10+a[i])%n; if(!vis[tmp]) q[++r]=tmp,num[r]=a[i],nxt[r]=l,vis[tmp]=1; } l++; } while(ans!=-1) { ANS[++tot]=num[ans]; ans=nxt[ans]; } Dow(i,1,tot) printf("%d",ANS[i]); }
-
12008-11-01 16:59:17@
(a*b) mod c=(a mod c*b mod c) mod c
(a+b) mod c=(a mod c+b mod c) mod c因此构图,一个余数对应一个点,对于每一个余数k,若(j*10+a[i]) mod n=l,则k与l连边,权为a[i]
求最短路即可
-
12006-05-24 20:42:04@
不用记录前面所有除过的数,只需要记录前面的余数。建一个图,图中的节点表示任意数除以n的余数,利用广搜,假设前一步的节点是x,那么下一步的节点就是(x*10+a[i]) mod n,两点间的权值是a[i],那么从0出发,当走回0的时候,一路上的权值全部连起来,就是所求的数字。其核心思想就是利用余数代表前面的运算结果,避免记录和处理太大的数。注意针对余数进行判重。
-
02018-07-28 13:34:28@
=<
题目没说答案范围,我一开始估计是100位数字以内,结果总是WA第一个点,我以为第一个点是小数字的边界问题,结果开成500位就AC了。。DP+按模分类
#include <bits/stdc++.h> using namespace std; #define FOR(i,n) for (int i=1;i<=n;i++) #define REP(i,a,b) for (int i=a;i<=b;i++) #define pb push_back #define mp make_pair #define ll long long #define pos(x,y) (x+(y)*n) const int N=100000+10; const int inf=0x3f3f3f3f; const ll mod=1000000007; const double eps=1e-8; int n,m; int a[20]; int f[510][10][5010]; int ten[510]; int main() { //freopen("in.txt","r",stdin); //freopen("out.txt","w",stdout); cin>>n>>m; FOR(i,m) { int t;cin>>t; a[t]=1; } if (n<10) { FOR(i,9) { if (n*i<10&&a[n*i]) { cout<<n*i<<endl; return 0; } } } REP(i,0,9) if (a[i]) f[1][i][i%n]=1; ten[0]=1; FOR(i,500) ten[i]=ten[i-1]*10%n; FOR(i,500) { REP(j,0,9) if (a[j]) REP(j2,0,9) if (a[j2]) { REP(k,0,n-1) { f[i+1][j2][(j2*ten[i]+k)%n]|=f[i][j][k]; } } } REP(i,2,500) FOR(j,9) if (a[j]) { if (f[i][j][0]) { int s=j; cout<<s; int t=(n-(j*ten[i-1])%n)%n; int now=i-1; while (now) { REP(k,0,9) if (a[k]) { if (f[now][k][t]) { cout<<k; t=(n+t-(k*ten[now-1])%n)%n; break; } } now--; } return 0; } } return 0; }
-
02009-11-02 19:42:59@
核心代码
for j:=0 to n-1 do
if v then
for k:=1 to m do
begin
e:=(a[k]*x+j)mod n;
if not v then
begin
v:=true;
f:=a[k];
g:=j;
end else
if (a[k]0) then
if (a[k] -
02009-10-27 08:41:06@
编译通过...
├ 测试数据 01:答案正确... 0ms
├ 测试数据 02:答案正确... 0ms
├ 测试数据 03:答案正确... 0ms
├ 测试数据 04:答案正确... 0ms
├ 测试数据 05:答案正确... 0ms
├ 测试数据 06:答案正确... 0ms
├ 测试数据 07:答案正确... 0ms
├ 测试数据 08:答案正确... 0ms
├ 测试数据 09:答案正确... 0ms
├ 测试数据 10:答案正确... 0ms
---|---|---|---|---|---|---|---|-
Accepted 有效得分:100 有效耗时:0msorz花了我二十分钟...
BFS解决~
不过DP确实没想出来,膜拜想出DP并写出来秒杀的牛们...
OTL... -
02009-10-15 07:23:21@
如果你用了字符串,一定要用ansistring,否则就是第一个点的格式错误加运行超时
-
02009-09-12 15:27:00@
楼下神牛:
BFS可以拿余数判重……所以也可以AC
不过我为啥202了?
-
02009-10-15 09:27:28@
我第一个点TLE/格式错误
其他90分……
真是无语……我回楼下的。。。确实这样。。。
囧了。。。
谢谢。 -
02009-03-18 16:05:33@
莫非是中国剩余定理?
-
02009-01-16 19:00:53@
编译通过...
├ 测试数据 01:答案正确... 0ms
├ 测试数据 02:答案正确... 0ms
├ 测试数据 03:答案正确... 0ms
├ 测试数据 04:答案正确... 0ms
├ 测试数据 05:答案正确... 0ms
├ 测试数据 06:答案正确... 0ms
├ 测试数据 07:答案正确... 0ms
├ 测试数据 08:答案正确... 0ms
├ 测试数据 09:答案正确... 0ms
├ 测试数据 10:答案正确... 0ms
---|---|---|---|---|---|---|---|-
Accepted 有效得分:100 有效耗时:0ms
广搜即可 -
02009-01-12 16:28:35@
...
-
02008-11-06 09:57:40@
编译通过...
├ 测试数据 01:答案正确... 0ms
├ 测试数据 02:答案正确... 0ms
├ 测试数据 03:答案正确... 0ms
├ 测试数据 04:答案正确... 0ms
├ 测试数据 05:答案正确... 0ms
├ 测试数据 06:答案正确... 0ms
├ 测试数据 07:答案正确... 0ms
├ 测试数据 08:答案正确... 0ms
├ 测试数据 09:答案正确... 0ms
├ 测试数据 10:答案正确... 0ms
---|---|---|---|---|---|---|---|-
Accepted 有效得分:100 有效耗时:0ms
dp
f表示i位的数字中,mod n 余数为j 所有数中的最小数,它第i位的数字
再用一个数组dist记录路径,即f的前驱数字.从i=1开始判断,向i+1 进行扩散. 每次判断时,若f还没取到过,则直接添加,若取到过,则用dist推出原序列以及新序列,从高位到低位判断新序列是否比原序列小,如果小则替换.直到取到了f.最后用dist推出i位序列可得 -
02008-11-01 16:29:18@
感谢吴豪..
令我恍然大虎..
``原来余数可以这样转换的..
好弱的数据..
我自己写了一组.
44440
10
44
88242
52
24
346
241
254
123褂掉..抱着试试的心态交上去..竟然..A了..
-
02008-10-28 12:59:48@
编译通过...
├ 测试数据 01:答案正确... 72ms
├ 测试数据 02:答案正确... 0ms
├ 测试数据 03:答案正确... 0ms
├ 测试数据 04:答案正确... 0ms
├ 测试数据 05:答案正确... 0ms
├ 测试数据 06:答案正确... 0ms
├ 测试数据 07:答案正确... 0ms
├ 测试数据 08:答案正确... 0ms
├ 测试数据 09:答案正确... 0ms
├ 测试数据 10:答案正确... 0ms
---|---|---|---|---|---|---|---|-
Accepted 有效得分:100 有效耗时:72ms我晕!!
qwe1 大牛 怎么压到22行啊!!
我58行!第一个点好慢啊 -
02008-10-27 19:14:11@
编译通过...
├ 测试数据 01:答案正确... 0ms
├ 测试数据 02:答案正确... 0ms
├ 测试数据 03:答案正确... 0ms
├ 测试数据 04:答案正确... 0ms
├ 测试数据 05:答案正确... 0ms
├ 测试数据 06:答案正确... 0ms
├ 测试数据 07:答案正确... 0ms
├ 测试数据 08:答案正确... 0ms
├ 测试数据 09:答案正确... 0ms
├ 测试数据 10:答案正确... 0ms
---|---|---|---|---|---|---|---|-
Accepted 有效得分:100 有效耗时:0ms
明显的装箱问题的DP不知道怎么扯那么远 -
02008-10-25 10:08:15@
高精吗?
-
02008-10-22 20:40:42@
暴力猥琐+高精=超时
-
02008-10-20 20:40:55@
DP
f[i][j]表示i位的,模n余j的最小可能值.不可能则为空。 -
02008-10-17 18:03:58@
我dp的.
string x[i][j]表示i位的,除n余数是j的最小是几.不可能就是"";
需要注意的是位数很多 我之前以为100已经够了,结果第一点挂了.改为1000就没问题了.可以用滚动数组,不过鉴于数据规模,不用也能过