poj 1027 深搜
题意:在一个固定大小为10x15的矩形区域A内被RGB三种颜色的小球填满。
现在按如下步骤操作:
1、 删除区域A内最大的一片区域M(任意颜色都可以,只要其占有区域最大)
2、 删除M后,自然会出现空的位置,在M区域上方的小球自然下落;当删除M后出现空列时,右边的列往左填充。注意是以“列”为单位填充,非空列只能整列往空列移动。移动后,各个小球之间的相对顺序 与 移动前一样。
3、 当区域A剩余小球数为0,或A内的最大区域为1时,游戏结束。
char b[10][16],c[10][16]; int best_i,best_j,best_cnt; int now_i, now_j, now_cnt; int score; void dfs(int i,int j){ if(j<now_j) now_j=j; if(j==now_j&&i>now_i) now_i=i; now_cnt++; b[i][j]='1'; if(i-1>=0&&c[i-1][j]==c[i][j]&&b[i-1][j]=='0') dfs(i-1,j); if(i+1<10&&c[i+1][j]==c[i][j]&&b[i+1][j]=='0') dfs(i+1,j); if(j-1>=0&&c[i][j-1]==c[i][j]&&b[i][j-1]=='0') dfs(i,j-1); if(j+1<15&&c[i][j+1]==c[i][j]&&b[i][j+1]=='0') dfs(i,j+1); } void mark(int i,int j) { //最大区域标记为2 best_cnt++; b[i][j]='2'; if(i-1>=0&&c[i-1][j]==c[i][j]&&b[i-1][j]!='2') mark(i-1,j); if(i+1<10&&c[i+1][j]==c[i][j]&&b[i+1][j]!='2') mark(i+1,j); if(j-1>=0&&c[i][j-1]==c[i][j]&&b[i][j-1]!='2') mark(i,j-1); if(j+1<15&&c[i][j+1]==c[i][j]&&b[i][j+1]!='2') mark(i,j+1); } void init(){ // cout<<" init"<<endl; for(int i=0;i<10;i++) for(int j=0;j<15;j++) b[i][j]='0'; best_i=best_j=16; best_cnt=0; } void prepare(){ // cout<<" prepare"<<endl; for(int j=0;j<15;j++) //确定当前最大数量和相应的最左下角的坐标 for(int i=9;i>=0;i--) if(b[i][j]=='0'&&c[i][j]!='x') { now_cnt=0; now_i=i; now_j=j; dfs(i,j); //深搜 if(now_cnt>best_cnt) { best_cnt=now_cnt; best_i=now_i; best_j=now_j; // cout<<best_i<<' '<<best_j<<' '<<best_cnt<<endl; } else if(now_cnt==best_cnt) { if(now_j<best_j) { best_i=now_i; best_j=now_j; } else if(now_j==best_j&&now_i>best_i) best_i=now_i; } } } void move() { // cout<<" move"<<endl; for(int j=0;j<15;j++) for(int i=9;i>=0;i--) if(b[i][j]=='2') { int m=i,n=j; int num=0; while(m>=0&&b[m][n]=='2') { num++; m--; } for(m=i;m-num>=0;m--) { c[m][n]=c[m-num][n]; b[m][n]=b[m-num][n]; } for(;m>=0;m--) { c[m][n]='x'; b[m][n]='x'; } } for(int j=0;j<15;j++) if(c[9][j]=='x') { int n=j,num=0; while(n<15&&c[9][n]=='x') { num++; n++; } if(n==15) break; for(int i=0;i<10;i++) { for(n=j;n+num<15;n++) { c[i][n]=c[i][n+num]; b[i][n]=b[i][n+num]; } for(;n<15;n++) { c[i][n]='x'; b[i][n]='x'; } } } } void readData() { for(int i=0;i<10;i++) cin>>c[i]; } int main() { int t; cin>>t; for(int r=1;r<=t;r++) { readData(); cout<<"Game "<<r<<":"<<endl<<endl; score=0; int cnt=0; int num=150; while(1) { init(); prepare(); if(best_cnt==1) break; if(best_cnt==0) { score+=1000; break; } best_cnt=0; mark(best_i,best_j); cnt++; num-=best_cnt; int points=(best_cnt-2)*(best_cnt-2); score+=points; cout<<"Move "<<cnt<<" at ("<<10-best_i<<","<<best_j+1<<"): removed "<<best_cnt<<" balls of color "<<c[best_i][best_j]<<", got "<<points<<" points. "<<endl; move(); } cout<<"Final score: "<<score<<", with "<<num<<" balls remaining."<<endl<<endl; } return 0; }