插头DP小结

首先是CDQ《基于连通性状态压缩的动态规划问题》论文上的题目:

URAL 1519 Formula

  1 #include <iostream>
  2 #include <cstdio>
  3 #include <cstring>
  4 using namespace std;
  5 const int maxn = 15;
  6 const int HASH = 30007;
  7 const int SIZE = 1000010;
  8 typedef long long LL;
  9 int N,M,maze[maxn][maxn],code[maxn],ch[maxn],ex,ey;
 10 char b[maxn];
 11 
 12 struct Hashmap{
 13     int e,first[HASH],next[SIZE];
 14     LL state[SIZE],f[SIZE];
 15 
 16     void init(){
 17         e = 0;
 18         memset(first,-1,sizeof(first));
 19     }
 20 
 21     void push(LL st,LL ans){
 22         int h = st%HASH;
 23         for(int i = first[h];i != -1;i = next[i])
 24         if(state[i] == st){
 25             f[i] += ans;
 26             return;
 27         }
 28         state[e] = st;
 29         f[e] = ans;
 30         next[e] = first[h];
 31         first[h] = e++;
 32     }
 33 }dp[2];
 34 
 35 void update(int *code,int len){
 36     for(int i = len;i >= 1;i--)
 37         code[i] = code[i-1];
 38     code[0] = 0;
 39 }
 40 
 41 void decode(int *code,int len,LL st){
 42     for(int i = len;i >= 0;i--){
 43         code[i] = st&7;
 44         st >>= 3;
 45     }
 46 }
 47 
 48 LL encode(int *code,int len){
 49     int cnt = 1;
 50     memset(ch,-1,sizeof(ch));
 51     ch[0] = 0;
 52     LL st = 0;
 53     for(int i = 0;i <= len;i++){
 54         if(ch[code[i]] == -1){
 55             ch[code[i]] = cnt++;
 56         }
 57         code[i] = ch[code[i]];
 58         st <<= 3;
 59         st |= code[i];
 60     }
 61     return st;
 62 }
 63 
 64 void dpblank(int i,int j,int now,int pre){
 65     int left,up,t;
 66     for(int k = 0;k < dp[pre].e;k++){
 67         decode(code,M,dp[pre].state[k]);
 68         left = code[j-1],up = code[j];
 69 
 70         if(left && up){
 71             if(left == up){
 72                 if(i == ex && j == ey){
 73                     code[j-1] = code[j] = 0;
 74                     if(j == M)  update(code,M);
 75                     dp[now].push(encode(code,M),dp[pre].f[k]);
 76                 }
 77             }
 78             else{
 79                 code[j-1] = code[j] = 0;
 80                 for(t = 0;t <= M;t++){
 81                     if(code[t] == up)   code[t] = left;
 82                 }
 83                 if(j == M)  update(code,M);
 84                 dp[now].push(encode(code,M),dp[pre].f[k]);
 85             }
 86         }else if((!left && up) ||(left && !up)){
 87             if(left) t = left;
 88             else    t = up;
 89             if(maze[i][j+1]){
 90                 code[j-1] = 0,code[j] = t;
 91                 dp[now].push(encode(code,M),dp[pre].f[k]);
 92             }
 93             if(maze[i+1][j]){
 94                 code[j-1] = t,code[j] = 0;
 95                 if(j == M)  update(code,M);
 96                 dp[now].push(encode(code,M),dp[pre].f[k]);
 97             }
 98         }else{
 99             if(maze[i+1][j] && maze[i][j+1]){
100                 code[j-1] = code[j] = 13;
101                 dp[now].push(encode(code,M),dp[pre].f[k]);
102             }
103         }
104     }
105 }
106 
107 void dpblock(int i,int j,int now,int pre){
108     for(int k = 0;k < dp[pre].e;k++){
109         decode(code,M,dp[pre].state[k]);
110         code[j-1] = code[j] = 0;
111         if(j == M)  update(code,M);
112         dp[now].push(encode(code,M),dp[pre].f[k]);
113     }
114 }
115 
116 int main()
117 {
118     while(scanf("%d%d",&N,&M) != EOF){
119         memset(maze,0,sizeof(maze));
120         ex = 0;
121         for(int i = 1;i <= N;i++){
122             scanf("%s",b+1);
123             for(int j = 1;j <= M;j++)
124                 if(b[j] == '.') maze[ex=i][ey=j] = 1;
125         }
126         if(ex == 0){
127             printf("0\n");
128             continue;
129         }
130         int now = 0,pre = 1;
131         dp[now].init();
132         dp[now].push(0,1);
133         for(int i = 1;i <= N;i++){
134             for(int j = 1;j <= M;j++){
135                 swap(now,pre);
136                 dp[now].init();
137                 if(maze[i][j])  dpblank(i,j,now,pre);
138                 else            dpblock(i,j,now,pre);
139             }
140         }
141         LL ans = 0;
142         for(int i = 0;i < dp[now].e;i++)
143             ans += dp[now].f[i];
144         printf("%I64d\n",ans);
145     }
146     return 0;
147 }
View Code

POJ 1739 Tony's Tour

  1 #include <iostream>
  2 #include <cstdio>
  3 #include <cstring>
  4 using namespace std;
  5 const int maxn = 15;
  6 const int HASH = 30007;
  7 const int SIZE = 1000010;
  8 typedef long long LL;
  9 int N,M,maze[maxn][maxn],code[maxn],ch[maxn],ex,ey;
 10 char b[maxn];
 11 
 12 struct Hashmap{
 13     int e,first[HASH],next[SIZE];
 14     LL state[SIZE],f[SIZE];
 15 
 16     void init(){
 17         e = 0;
 18         memset(first,-1,sizeof(first));
 19     }
 20 
 21     void push(LL st,LL ans){
 22         int h = st%HASH;
 23         for(int i = first[h];i != -1;i = next[i])
 24         if(state[i] == st){
 25             f[i] += ans;
 26             return;
 27         }
 28         state[e] = st;
 29         f[e] = ans;
 30         next[e] = first[h];
 31         first[h] = e++;
 32     }
 33 }dp[2];
 34 
 35 void update(int *code,int len){
 36     for(int i = len;i >= 1;i--)
 37         code[i] = code[i-1];
 38     code[0] = 0;
 39 }
 40 
 41 void decode(int *code,int len,LL st){
 42     for(int i = len;i >= 0;i--){
 43         code[i] = st&7;
 44         st >>= 3;
 45     }
 46 }
 47 
 48 LL encode(int *code,int len){
 49     int cnt = 1;
 50     memset(ch,-1,sizeof(ch));
 51     ch[0] = 0;
 52     LL st = 0;
 53     for(int i = 0;i <= len;i++){
 54         if(ch[code[i]] == -1){
 55             ch[code[i]] = cnt++;
 56         }
 57         code[i] = ch[code[i]];
 58         st <<= 3;
 59         st |= code[i];
 60     }
 61     return st;
 62 }
 63 
 64 void dpblank(int i,int j,int now,int pre){
 65     int left,up,t;
 66     for(int k = 0;k < dp[pre].e;k++){
 67         decode(code,M,dp[pre].state[k]);
 68         left = code[j-1],up = code[j];
 69 
 70         if(left && up){
 71             if(left == up){
 72                 if(i == ex && j == ey){
 73                     code[j-1] = code[j] = 0;
 74                     if(j == M)  update(code,M);
 75                     dp[now].push(encode(code,M),dp[pre].f[k]);
 76                 }
 77             }
 78             else{
 79                 code[j-1] = code[j] = 0;
 80                 for(t = 0;t <= M;t++){
 81                     if(code[t] == up)   code[t] = left;
 82                 }
 83                 if(j == M)  update(code,M);
 84                 dp[now].push(encode(code,M),dp[pre].f[k]);
 85             }
 86         }else if((!left && up) ||(left && !up)){
 87             if(left) t = left;
 88             else    t = up;
 89             if(maze[i][j+1]){
 90                 code[j-1] = 0,code[j] = t;
 91                 dp[now].push(encode(code,M),dp[pre].f[k]);
 92             }
 93             if(maze[i+1][j]){
 94                 code[j-1] = t,code[j] = 0;
 95                 if(j == M)  update(code,M);
 96                 dp[now].push(encode(code,M),dp[pre].f[k]);
 97             }
 98         }else{
 99             if(maze[i+1][j] && maze[i][j+1]){
100                 code[j-1] = code[j] = 13;
101                 dp[now].push(encode(code,M),dp[pre].f[k]);
102             }
103         }
104     }
105 }
106 
107 void dpblock(int i,int j,int now,int pre){
108     for(int k = 0;k < dp[pre].e;k++){
109         decode(code,M,dp[pre].state[k]);
110         code[j-1] = code[j] = 0;
111         if(j == M)  update(code,M);
112         dp[now].push(encode(code,M),dp[pre].f[k]);
113     }
114 }
115 
116 int main()
117 {
118     while(scanf("%d%d",&N,&M),N+M){
119         memset(maze,0,sizeof(maze));
120         for(int i = 1;i <= N;i++){
121             scanf("%s",b+1);
122             for(int j = 1;j <= M;j++)
123                 if(b[j] == '.') maze[i][j] = 1;
124         }
125         maze[N+1][1] = maze[N+1][M] = 1;
126         for(int i = 2;i < M;i++)    maze[N+1][i] = 0;
127         for(int i = 1;i <= M;i++)   maze[N+2][i] = 1;
128         N += 2;
129         ex = N,ey = M;
130 
131         int now = 0,pre = 1;
132         dp[now].init();
133         dp[now].push(0,1);
134         for(int i = 1;i <= N;i++){
135             for(int j = 1;j <= M;j++){
136                 swap(now,pre);
137                 dp[now].init();
138                 if(maze[i][j])  dpblank(i,j,now,pre);
139                 else            dpblock(i,j,now,pre);
140             }
141         }
142         LL ans = 0;
143         for(int i = 0;i < dp[now].e;i++)
144             ans += dp[now].f[i];
145         printf("%I64d\n",ans);
146     }
147     return 0;
148 }
View Code

UVA 10572 Black and White

  1 #include <cstdio>
  2 #include <cstring>
  3 #include <algorithm>
  4 using namespace std;
  5 const int HASH = 10007;
  6 const int SIZE = 10000;
  7 int N,M;
  8 char maze[10][10];
  9 int pre[65][SIZE],opt[65][SIZE];
 10 
 11 struct Hashmap{
 12     int e,first[HASH],next[SIZE];
 13     int color[SIZE],state[SIZE],f[SIZE];
 14 
 15     void init(){
 16         e = 0;
 17         memset(first,-1,sizeof(first));
 18     }
 19 
 20     void push(int st,int col,int ans,int id,int k,char ch){
 21         int h = ((st<<6)+col) % HASH;
 22         for(int i = first[h];i != -1;i = next[i])
 23             if(state[i] == st && color[i] == col){
 24                 f[i] += ans;
 25                 return;
 26             }
 27         state[e] = st;
 28         color[e] = col;
 29         f[e] = ans;
 30         pre[id][e] = k;
 31         opt[id][e] = ch;
 32         next[e] = first[h];
 33         first[h] = e++;
 34     }
 35 }dp[2];
 36 
 37 int code[10],ch[10];
 38 
 39 void decode(int *code,int len,int st){
 40     for(int i = len-1;i >= 0;i--){
 41         code[i] = st&7;
 42         st >>= 3;
 43     }
 44 }
 45 
 46 int encode(int *code,int len){
 47     int st = 0,cnt = 0;
 48     memset(ch,-1,sizeof(ch));
 49     for(int i = 0;i < len;i++){
 50         if(ch[code[i]] == -1)
 51             ch[code[i]] = cnt++;
 52         st = st<<3|ch[code[i]];
 53     }
 54     return st;
 55 }
 56 
 57 void DP(int i,int j,int c,int now,int pre){
 58     for(int k = 0;k < dp[pre].e;k++){
 59         int col = dp[pre].color[k];
 60         int up = i ? ((col>>j)&1)==c : 0;
 61         int left = j ? (col>>(j-1)&1)==c : 0;
 62         int lu = (col>>M)== c;
 63         if(up && left && lu)    continue;
 64         if(i == N-1 && j == M-1 && !up && !left && lu)  continue;
 65         decode(code,M,dp[pre].state[k]);
 66         if(i && !up){
 67             int s1 = 0,s2 = 0;
 68             for(int t = 0;t < M;t++){
 69                 if(code[t] == code[j])  s1++;
 70                 if(((col>>t)&1) != c)   s2++;
 71             }
 72             if(s1 == 1){
 73                 if(s2 > 1)  continue;
 74                 if(i < N-1 || j < M-2)  continue;
 75             }
 76         }
 77         if(up && left){
 78             if(code[j] != code[j-1]){
 79                 for(int t = 0,x = code[j];t < M;t++)
 80                     if(code[t] == x)    code[t] = code[j-1];
 81             }
 82         }
 83         else if(!up && left)    code[j] = code[j-1];
 84         else if(!up && !left)   code[j] = M;
 85 
 86         if(col&(1<<j))  col |= (1<<M);
 87         else            col &= ~(1<<M);
 88         if(c)           col |= (1<<j);
 89         else            col &= ~(1<<j);
 90         dp[now].push(encode(code,M),col,dp[pre].f[k],i*M+j,k,c ? '#' : 'o');
 91     }
 92 }
 93 
 94 void print(int k){
 95     for(int i = N-1;i >= 0;i--)
 96         for(int j = M-1;j >= 0;j--)
 97             maze[i][j] = opt[i*M+j][k],k = pre[i*M+j][k];
 98     for(int i = 0;i < N;i++)    puts(maze[i]);
 99 }
100 
101 int main(){
102     //freopen("input.txt","r",stdin);
103     int kase;
104     scanf("%d",&kase);
105     while(kase--){
106         scanf("%d%d",&N,&M);
107         for(int i = 0;i < N;i++)
108             scanf("%s",maze[i]);
109         int now = 0,pre = 1;
110         int ans = 0;
111         dp[now].init();
112         dp[now].push(0,0,1,0,0,0);
113         for(int i = 0;i < N;i++)
114             for(int j = 0;j < M;j++){
115                 now ^= 1,pre ^= 1;
116                 dp[now].init();
117                 if(maze[i][j] != '#')   DP(i,j,0,now,pre);
118                 if(maze[i][j] != 'o')   DP(i,j,1,now,pre);
119             }
120 
121         int k;
122         for(int i = 0;i < dp[now].e;i++){
123             int tmp = 0;
124             decode(code,M,dp[now].state[i]);
125             for(int j = 0;j < M;j++)
126                 tmp = max(tmp,code[j]);
127             if(tmp > 1) continue;
128             ans += dp[now].f[i],k = i;
129         }
130         printf("%d\n",ans);
131         if(ans != 0)    print(k);
132     }
133     return 0;
134 }
View Code

HYSBZ 1494 生成树计数

  1 #include <iostream>
  2 #include <cstdio>
  3 #include <cstring>
  4 #include <algorithm>
  5 using namespace std;
  6 const int N = 1<<6;
  7 const int MOD = 65521;
  8 int K,tot_status,f[N],fa[10];
  9 int status[N],ord[1<<16];
 10 long long n;
 11 struct Matrix{
 12     long long mat[N][N];
 13     Matrix operator*(const Matrix m)const{
 14         Matrix tmp;
 15         for(int i = 0;i < tot_status;i++){
 16             for(int j = 0;j < tot_status;j++){
 17                 tmp.mat[i][j] = 0;
 18                 for(int k = 0;k < tot_status;k++){
 19                     tmp.mat[i][j] += mat[i][k]*m.mat[k][j]%MOD;
 20                     tmp.mat[i][j] %= MOD;
 21                 }
 22             }
 23         }
 24         return tmp;
 25     }
 26 };
 27 
 28 long long Pow(Matrix &m,long long n){
 29     Matrix ans;
 30     memset(ans.mat,0,sizeof(ans.mat));
 31     for(int i = 0;i < tot_status;i++)
 32         ans.mat[i][i] = 1;
 33     n -= K;
 34     while(n){
 35         if(n&1) ans = ans*m;
 36         n >>= 1;
 37         m = m*m;
 38     }
 39     long long sum = 0;
 40     for(int i = 0;i < tot_status;i++){
 41         sum += ans.mat[0][i]*f[i];
 42         sum %= MOD;
 43     }
 44     return sum;
 45 }
 46 
 47 bool check(int st){
 48     int tmp = 0;
 49     for(int i = 0;i < K;i++){
 50         int tp = (st>>(i*3))&7;tmp |= (1<<tp);
 51         for(int j = 1;j <= tp;j++)  if(!(tmp&(1<<j)))   return 0;
 52     }
 53     return 1;
 54 }
 55 
 56 void dfs(int dep,int st){
 57     if(dep == K){
 58         if(check(st))   ord[st] = tot_status,status[tot_status++] = st;
 59         return;
 60     }
 61     for(int i = 1;i <= K;i++)   dfs(dep+1,st|(i<<(3*dep)));
 62 }
 63 
 64 int find(int x){
 65     return fa[x] == x ? x : fa[x] = find(fa[x]);
 66 }
 67 
 68 int main()
 69 {
 70     //freopen("output.txt","w",stdout);
 71     scanf("%d%lld",&K,&n);
 72     tot_status = 0;
 73     dfs(1,1);
 74     Matrix m;
 75     memset(m.mat,0,sizeof(m.mat));
 76     for(int i = 0;i < tot_status;i++){
 77         f[i] = 1;
 78         int cnt[10];
 79         memset(cnt,0,sizeof(cnt));
 80         for(int j = 0;j < K;j++)
 81             cnt[status[i]>>(j*3)&7]++;
 82         for(int j = 1;j <= K;j++){
 83             if(cnt[j] == 3) f[i] = 3;
 84             if(cnt[j] == 4) f[i] = 16;
 85             if(cnt[j] == 5) f[i] = 125;
 86         }
 87         for(int s = 0;s < (1<<K);s++){
 88             for(int j = 0;j <= K;j++)   fa[j] = j;
 89             for(int j = 0;j < K;j++){
 90                 for(int k = j+1;k < K;k++)
 91                     if(((status[i]>>(j*3))&7) == ((status[i]>>(k*3))&7))
 92                         fa[find(j)] = find(k);
 93             }
 94             bool flag = 1;
 95             for(int j = 0;j < K;j++)if(s&(1<<j)){
 96                 if(find(j) == find(K)){flag = 0;break;}
 97                 else    fa[find(j)] = find(K);
 98             }
 99             if(!flag)   continue;
100             flag = 0;
101             for(int j = 1;j <= K;j++)
102                 if(find(0) == find(j)){flag = 1;break;}
103             if(!flag)   continue;
104             int use = 0,nxt = 0;
105             for(int j = 0;j < K;j++)if(!(nxt&(7<<(j*3)))){
106                 nxt |= ++use<<(j*3);
107                 for(int k = j+1;k < K;k++)
108                     if(find(j+1) == find(k+1))  nxt |= use<<(k*3);
109             }
110             m.mat[ord[nxt]][i]++;
111         }
112     }
113     printf("%lld\n",Pow(m,n));
114     return 0;
115 }
View Code

ZOJ 2125 Rocket Mania

  1 #include <cstdio>
  2 #include <cstring>
  3 #include <cstdlib>
  4 #define get(x,t) (((x) >> (t)) & 1)
  5 #define get2(x,t) (((x) >> (t<<2)) &15)
  6 const int HASH = 30007;
  7 const int SIZE = 100000;
  8 const int maxn = 10;
  9 typedef long long LL;
 10 struct Node{
 11     int s1;
 12     LL s2;
 13 };
 14 char map[maxn][maxn];
 15 int code[maxn],ch[maxn];
 16 Node best;
 17 int last,n;
 18 struct Hashmap{
 19     int e,first[HASH],next[SIZE];
 20     Node node[SIZE];
 21 
 22     void init(){
 23         e = 0;
 24         memset(first,-1,sizeof(first));
 25     }
 26 
 27     void push(int s1,LL s2){
 28         int h = abs(s1*s2+s1+s2) % HASH;
 29         for(int i = first[h];i != -1;i = next[i])
 30             if(node[i].s1 == s1 && node[i].s2 == s2)
 31                 return;
 32         node[e].s1 = s1,node[e].s2 = s2;
 33         next[e] = first[h];
 34         first[h] = e++;
 35     }
 36 }dp[2];
 37 
 38 void decode(int *code,LL st){
 39     for(int i = 0;i <= 9;i++,st >>= 4)
 40         code[i] = st&15;
 41 }
 42 
 43 LL encode(int *code){
 44     LL st = 0;
 45     int cnt = 1;
 46     memset(ch,-1,sizeof(ch));
 47     for(int i = 9;i >= 0;i--){
 48         if(code[i] && ch[code[i]] == -1)
 49             ch[code[i]] = cnt++;
 50         if(code[i]) code[i] = ch[code[i]];
 51         st = st<<4;
 52         st |= code[i];
 53     }
 54     return st;
 55 }
 56 
 57 void update(int *code){
 58     for(int i = 9;i >= 1;i--)
 59         code[i] = code[i-1];
 60     code[0] = 0;
 61 }
 62 
 63 int merge(int fire,int a,int b){
 64     int t = get(fire,a)|get(fire,b);
 65     a = code[a],b = code[b];
 66     for(int i = 0;i <= 9;i++)
 67         if(code[i] == b)   code[i] = a;
 68     for(int i = 0;i <= 9;i++)
 69         if(code[i] == a)   fire |= (t<<i);
 70     return fire;
 71 }
 72 
 73 Node check(Node t){
 74     for(int i = 0;i <= 9;i++)
 75     if(get2(t.s2,i) && !get(t.s1,i)){
 76         bool flag = 1;
 77         for(int j = 0;j <= 9;j++)
 78         if(i != j && get2(t.s2,i) == get2(t.s2,j)){
 79             flag = 0;
 80             break;
 81         }
 82         if(flag)    t.s2 ^= (get2(t.s2,i)<<(i<<2));
 83     }
 84     return t;
 85 }
 86 
 87 void insert(int s1,LL s2,int now){
 88     if(!s1) return;
 89     bool flag = 1;
 90     for(int i = 0;i <= 9;i++)
 91     if(get2(s2,i) && !get(best.s1,i)){
 92         flag = 0;break;
 93     }
 94     if(flag)    return;
 95     int tmp1 = 0,tmp2 = 0;
 96     for(int i = 0;i <= 9;i++)
 97         tmp1 += get(s1,i),tmp2 += get(best.s1,i);
 98     if(tmp1 > tmp2) best.s1 = s1,best.s2 = s2;
 99     if(last != -1){
100         for(int i = 0;i <= last;i++)
101         if(!get(s1,i) && get2(s2,i)){
102             flag = 1;
103             for(int t = last+1;t <= 9;t++)
104                 if(get2(s2,i) == get2(s2,t)){
105                     flag = 0;break;
106                 }
107             if(flag)    s2 ^= (get2(s2,i)<<(i<<2));
108         }
109         decode(code,s2),s2 = encode(code);
110     }
111     dp[now].push(s1,s2);
112 }
113 
114 int DP(){
115     int t = 1<<n-1;
116     code[9] = 0;
117     for(int i = 0;i < 9;i++){
118         if(get(t,i))    code[i] = 1;
119         else            code[i] = 0;
120     }
121     best.s1 = 0,best.s2 = 0;
122     int now = 0,pre = 1;
123     dp[now].init();
124     insert(t,encode(code),now);
125     last = -1;
126     for(int j = -1;j < 6;j++){
127         for(int i = j == -1 ? 8 : 0;i < 9;i++){
128             now ^= 1,pre ^= 1;
129             dp[now].init();
130             best.s1 = best.s2 = 0;
131 
132             for(int k = 0;k < dp[pre].e;k++){
133                 Node t = dp[pre].node[k];
134                 t = check(t);
135                 decode(code,t.s2);
136                 if(i == 0){
137                     update(code);
138                     t.s2 = encode(code);
139                     int tmp = get(t.s1,9);
140                     t.s1 ^= (tmp << 9);
141                     t.s1 <<= 1;
142                 }
143                 int up = code[i],left = code[i+1];
144                 int a1 = get(t.s1,i),a2 = get(t.s1,i+1);
145                 last = (j == 5 ? i : -1);
146 
147                 if(map[i][j] == '.'){
148                     decode(code,t.s2);
149                     code[i] = code[i+1] = 0;
150                     insert(t.s1^(a1<<i)^(a2<<i+1),encode(code),now);
151                 }else if(map[i][j] == 'L'){
152                     decode(code,t.s2);
153                     code[i] = code[i+1] = 9;
154                     insert(t.s1^(a1<<i)^(a2<<i+1),encode(code),now);
155                     if(up){
156                         decode(code,t.s2);
157                         code[i+1] = 0;
158                         insert(t.s1^(a2<<i+1),encode(code),now);
159                     }
160                     if(left){
161                         decode(code,t.s2);
162                         code[i] = 0;
163                         insert(t.s1^(a1<<i),encode(code),now);
164                     }
165                     if(left && up){
166                         decode(code,t.s2);
167                         int fire = merge(t.s1,i,i+1);
168                         int p = a1|a2;
169                         code[i] = code[i+1] = 0;
170                         insert(fire^(p<<i)^(p<<i+1),encode(code),now);
171                     }
172                 }else if(map[i][j] == '-'){
173                     if(!left&&!up){
174                         decode(code,t.s2);
175                         code[i] = code[i+1] = 0;
176                         insert(t.s1^(a1<<i)^(a2<<i+1),encode(code),now);
177                     }
178                     if(up){
179                         decode(code,t.s2);
180                         code[i+1] = code[i],code[i] = 0;
181                         insert(t.s1^(a1<<i)^(a2<<i+1)^(a1<<i+1),encode(code),now);
182                     }
183                     if(left){
184                         decode(code,t.s2);
185                         code[i] = code[i+1],code[i+1] = 0;
186                         insert(t.s1^(a1<<i)^(a2<<i+1)^(a2<<i),encode(code),now);
187                     }
188                 }else if(map[i][j] == 'T'){
189                     if(up){
190                         decode(code,t.s2);
191                         code[i+1] = code[i];
192                         insert(t.s1^(a2<<i+1)^(a1<<i+1),encode(code),now);
193                     }else{
194                         decode(code,t.s2);
195                         code[i] = code[i+1] = 9;
196                         insert(t.s1^(a1<<i)^(a2<<i+1),encode(code),now);
197                     }
198                     if(left){
199                         decode(code,t.s2);
200                         code[i] = code[i+1];
201                         insert(t.s1^(a1<<i)^(a2<<i),encode(code),now);
202                     }else{
203                         decode(code,t.s2);
204                         code[i] = code[i+1] = 9;
205                         insert(t.s1^(a1<<i)^(a2<<i+1),encode(code),now);
206                     }
207                     if(up && left){
208                         decode(code,t.s2);
209                         int fire = merge(t.s1,i,i+1);
210                         int p = a1|a2;
211                         code[i] = 0;
212                         insert(fire^(p<<i),encode(code),now);
213                     }else if(up){
214                         decode(code,t.s2);
215                         code[i+1] = code[i],code[i] = 0;
216                         insert(t.s1^(a1<<i)^(a2<<i+1)^(a1<<i+1),encode(code),now);
217                     }else if(left){
218                         decode(code,t.s2);
219                         code[i] = 0;
220                         insert(t.s1^(a1<<i),encode(code),now);
221                     }
222                     if(up && left){
223                         decode(code,t.s2);
224                         int fire = merge(t.s1,i,i+1);
225                         int p = a1|a2;
226                         code[i+1] = 0;
227                         insert(fire^(p<<i+1),encode(code),now);
228                     }else if(up){
229                         decode(code,t.s2);
230                         code[i+1] = 0;
231                         insert(t.s1^(a2<<i+1),encode(code),now);
232                     }else if(left){
233                         decode(code,t.s2);
234                         code[i] = code[i+1],code[i+1] = 0;
235                         insert(t.s1^(a1<<i)^(a2<<i+1)^(a2<<i),encode(code),now);
236                     }
237                 }else{
238                     if(up && left){
239                         decode(code,t.s2);
240                         int fire = merge(t.s1,i,i+1);
241                         insert(fire,encode(code),now);
242                     }else if(up){
243                         decode(code,t.s2);
244                         code[i+1] = code[i];
245                         insert(t.s1^(a1<<i+1),encode(code),now);
246                     }else if(left){
247                         decode(code,t.s2);
248                         code[i] = code[i+1];
249                         insert(t.s1^(a2<<i),encode(code),now);
250                     }else{
251                         decode(code,t.s2);
252                         code[i+1] = code[i] = 9;
253                         insert(t.s1^(a1<<i)^(a2<<i+1),encode(code),now);
254                     }
255                 }
256             }
257         }
258     }
259 
260     int ans = 0;
261     for(int k = 0;k < dp[now].e;k++){
262         Node t = dp[now].node[k];
263         int tmp = 0;
264         for(int i = 0;i < 9;i++)
265             tmp += get(t.s1,i);
266         ans = tmp > ans ? tmp : ans;
267     }
268     printf("%d\n",ans);
269 }
270 
271 int main ()
272 {
273     while(scanf("%d",&n) != EOF){
274         for(int i = 0;i < 9;i++)
275             scanf("%s",map[i]);
276         DP();
277     }
278     return 0 ;
279 }
View Code

 

 

posted @ 2014-05-10 18:00  浙西贫农  阅读(279)  评论(0编辑  收藏  举报