Time Limit: 1000MS | Memory Limit: 10000K | |
Total Submissions: 4454 | Accepted: 1509 |
Description
........ ........ ........ ........ .CCC.... EEEEEE.. ........ ........ ..BBBB.. .C.C.... E....E.. DDDDDD.. ........ ..B..B.. .C.C.... E....E.. D....D.. ........ ..B..B.. .CCC.... E....E.. D....D.. ....AAAA ..B..B.. ........ E....E.. D....D.. ....A..A ..BBBB.. ........ E....E.. DDDDDD.. ....A..A ........ ........ E....E.. ........ ....AAAA ........ ........ EEEEEE.. ........ ........ ........ ........ 1 2 3 4 5
.CCC.... ECBCBB.. DCBCDB.. DCCC.B.. D.B.ABAA D.BBBB.A DDDDAD.A E...AAAA EEEEEE..
Input
Output
Sample Input
9 8 .CCC.... ECBCBB.. DCBCDB.. DCCC.B.. D.B.ABAA D.BBBB.A DDDDAD.A E...AAAA EEEEEE..
Sample Output
EDABC
Source
1.多组输出,有不确定的情况全部输出,按字典顺序排列. 2.图中的的frame均会给出4条边的情况(一个顶点包括2条边),可以推断出frame的长度和位置.
思路:
1.矩形的判定,由条件可知,每个矩形可以用四条边表示,横坐标最小upx与最大dowx,纵坐标最小ly与最大ry,来唯一确定。然后遍历这四条边确定出来的边框A。找出哪些边框B凌驾于该边框之上,则添加一条有向边从A到B。
2.然后就是DFS式的拓扑排序。
#include<stdio.h> #include<string.h> #include<vector> using namespace std; const int N = 40; struct frame { int ux,dx,ly,ry; //框架的四条边 }; bool exist[N]; int in[N],n,path[N]; vector<int>mapt[N]; void tope(int u,int k) { path[k]=u; if(k==n) { for(int i=1;i<=k;i++) printf("%c",path[i]+'A'); printf("\n"); return ; } in[u]=-1; int len=mapt[u].size(); for(int i=0;i<len;i++)//去边 in[mapt[u][i]]--; for(int i=0;i<26;i++) if(exist[i]&&in[i]==0)//条件:有i类边框,并且入度为0 tope(i,k+1); for(int i=0;i<len;i++)//还原边 in[mapt[u][i]]++; in[u]=0; } char str[N][N]; void buildMap(frame b[]) { bool have[N][N]={0}; int ch,l,r,x,y; for(int i=0;i<26;i++) if(exist[i]) { x=b[i].ux; l=b[i].ly; r=b[i].ry; while(l<=r) { if(str[x][l]!='.'&&str[x][l]-'A'!=i) { ch=str[x][l]-'A'; have[i][ch]=1; } l++; } x=b[i].dx; l=b[i].ly; r=b[i].ry; while(l<=r) { if(str[x][l]!='.'&&str[x][l]-'A'!=i) { ch=str[x][l]-'A'; have[i][ch]=1; } l++; } y=b[i].ly; l=b[i].ux; r=b[i].dx; while(l<=r) { if(str[l][y]!='.'&&str[l][y]-'A'!=i) { ch=str[l][y]-'A'; have[i][ch]=1; } l++; } y=b[i].ry; l=b[i].ux; r=b[i].dx; while(l<=r) { if(str[l][y]!='.'&&str[l][y]-'A'!=i) { ch=str[l][y]-'A'; have[i][ch]=1; } l++; } for(int j=0;j<26;j++) if(have[i][j]) { in[j]++; mapt[i].push_back(j); //j类边框重在i类边框之上 } } } int main() { frame board[N]; int h,w; while(scanf("%d",&h)>0) { scanf("%d",&w); n=0; for(int i=0;i<=30;i++) { mapt[i].clear(); in[i]=0; exist[i]=false; board[i].ux=board[i].ly=N; board[i].dx=board[i].ry=-1; } for(int i=0;i<h;i++) { scanf("%s",str[i]); for(int j=0;j<w;j++) if(str[i][j]!='.') { int ch=str[i][j]-'A'; exist[ch]=true; if(board[ch].ux>i) board[ch].ux=i; if(board[ch].dx<i) board[ch].dx=i; if(board[ch].ly>j) board[ch].ly=j; if(board[ch].ry<j) board[ch].ry=j; } } buildMap(board); for(int i=0;i<26;i++) if(exist[i]) n++; //记录有多少个不同类型的边框 for(int i=0;i<26;i++) if(exist[i]&&in[i]==0) tope(i,1); } }
POJ1128 Frame Stacking(拓扑排序)经典
原文:http://blog.csdn.net/u010372095/article/details/45342033