2 条题解
-
2shy LV 10 @ 2015-10-25 21:13:47
shy发现这题题解丢失了。。
作为我们今天模拟赛的原题之一,也顺便过来A掉。
我们咀嚼一下zhw大神的原话——
“若将一个数放大到无限大,则方案数为其它几个数能组成的方案数*2。
枚举当前到达第i个数,dp[j]为和为j时至少从哪儿开始才能构成j。然后对于每个数求出当不存在该数时方案总数即可。”
std相当精妙,也就是复制一遍数组,作两次背包,dp[j]表示和是j的情况下最右边的糖罐是哪个。通过这样可以模拟出缺少i-n+1时剩余糖果构造出的方案。具体可见代码。
第二问,介于题目后写明了From BOI 2010,度娘很容易就找到英文题解。英语不好的shy通读了一下,再加之zhw大神的提示,就反应过来。要求最小的数使之不等于任意xj-xi。“加加减减”,用数列-a1,a1,-a2,a2,...,-an,an构造即可。测试数据 #0: Accepted, time = 2 ms, mem = 9048 KiB, score = 10
测试数据 #1: Accepted, time = 0 ms, mem = 9052 KiB, score = 10
测试数据 #2: Accepted, time = 0 ms, mem = 9052 KiB, score = 10
测试数据 #3: Accepted, time = 1468 ms, mem = 9052 KiB, score = 10
测试数据 #4: Accepted, time = 1015 ms, mem = 9052 KiB, score = 10
测试数据 #5: Accepted, time = 593 ms, mem = 9048 KiB, score = 10
测试数据 #6: Accepted, time = 859 ms, mem = 9048 KiB, score = 10
测试数据 #7: Accepted, time = 1078 ms, mem = 9048 KiB, score = 10
测试数据 #8: Accepted, time = 1250 ms, mem = 9048 KiB, score = 10
测试数据 #9: Accepted, time = 1296 ms, mem = 9052 KiB, score = 10
Accepted, time = 7561 ms, mem = 9052 KiB, score = 100代码
var
n,k,s,i,j,tmp,ans:longint;
a,g:array[0..205]of longint;
f:array[0..700005]of longint;
h:array[-707005..707005]of longint;function max(a,b:longint):longint;
begin if a>b then exit(a); exit(b) end;begin
read(n);
for i:=1 to n do begin read(a[i]); inc(k,a[i]) end;
for i:=1+n to n<<1 do a[i]:=a[i-n];
for i:=1 to n<<1 do
begin
for j:=k downto a[i]+1 do
f[j]:=max(f[j],f[j-a[i]]);
f[a[i]]:=max(f[a[i]],i);
if i>=n then for j:=1 to k do
if f[j]>i-n+1 then inc(g[i-n+1])
end;
for i:=1 to n do if g[i]>tmp then
begin tmp:=g[i]; ans:=i end;
writeln(ans);
k:=0;
h[0]:=1;
for i:=1 to n do if i<>ans then begin inc(k,a[i]);
for j:=k downto a[i] do h[j]:=h[j]or h[j-a[i]] end;
for i:=1 to n do if i<>ans then begin dec(s,a[i]);
for j:=s to k-a[i] do h[j]:=h[j]or h[j+a[i]] end;
for i:=1 to k+1 do if h[i]=0 then break;
write(i)
end. -
02012-10-28 17:32:15@
过了一个点!
- 1