「CF268D」Wall Bars
题解
f(i,a,b,c,j)表示前i个踏板放在某根柱子,另外三根柱子最后的踏板与它距离分别为a,b,c,j表示第i号踏板是否有效(从地面能否到达它)
设计出状态后,转移就是考虑i+1号踏板放在哪根柱子上
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 |
#include<map> #include<set> #include<cmath> #include<cstdio> #include<cstring> #include<vector> #include<iostream> #define mod 1000000009 #define ll long long #define add(i,a,b,c,j,val) (f[i][min(a,h)][min(b,h)][min(c,h)][j]+=val)%=mod; using namespace std; ll read() { int x=0,f=1;char ch=getchar(); while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();} while(ch>='0'&&ch<='9'){x=x*10+ch-'0';ch=getchar();} return x*f; } int n,h,ans; int f[1005][35][35][35][2]; int main() { n=read();h=read(); f[1][1][1][1][1]=4; for(int i=1;i<n;i++) for(int a=1;a<=h;a++) for(int b=1;b<=h;b++) for(int c=1;c<=h;c++) for(int j=0;j<2;j++) if(f[i][a][b][c][j]) { add(i+1,a+1,b+1,c+1,j,f[i][a][b][c][j]); int d=1;if(j==0)d=h; add(i+1,d,b+1,c+1,a<h,f[i][a][b][c][j]); add(i+1,a+1,d,c+1,b<h,f[i][a][b][c][j]); add(i+1,a+1,b+1,d,c<h,f[i][a][b][c][j]); } for(int a=1;a<=h;a++) for(int b=1;b<=h;b++) for(int c=1;c<=h;c++) for(int j=0;j<2;j++) if(j||a<h||b<h||c<h) ans=(ans+f[n][a][b][c][j])%mod; printf("%d\n",ans); return 0; } |
这份代码随便一组数据就WA啊,比如209 21,答案应该是220082456
Orz LTY