トポロジーソートの例題(HDU 1285)
1954 ワード
試合の順位を決める
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others) Total Submission(s): 24346 Accepted Submission(s): 9798
Problem Description
Nチーム(1<=N<=500)があり、番号は1、2、3、...Nは試合を行い、試合が終わった後、審判委員会はすべての参加チームを行った後から順番に順位をつけなければならないが、現在、審判委員会は直接各チームの試合成績を得ることができず、各試合の結果、すなわちP 1がP 2に勝ったことしか知らず、P 1,P 2で表され、順位はP 1がP 2の前にある.今、プログラムを作ってランキングを確定してください.
Input
入力にはいくつかのグループがあり、各グループの第1の動作の2つの数N(1<=N<=500)、M;ここで、Nは行列の個数を表し、MはM行に続く入力データを表す.次のM行データでは、行ごとに2つの整数P 1があり、P 2はP 1チームがP 2チームに勝ったことを示す.
Output
要件に合致するランキングを与えます.出力時にキュー番号の間にスペースがあり、最後の名前の後ろにスペースがありません.
その他の説明:条件に合致する順位は唯一ではない可能性があります.この場合、出力時の番号の小さいチームが上位にあることが要求されます.入力データは正しいことを保証します.すなわち、入力データは必ず要求に合致するランキングを確保します.
Sample Input
4 3 1 2 2 3 4 3
Sample Output
1 2 4 3
既にAC済みのコード:
#include #include #include using namespace std; int main() { int map[550][550],in[2100],ans[2100]; int n,m,a,b,t; while(scanf("%d %d",&n,&m)!=EOF) { memset(map,0,sizeof(map)); memset(in,0,sizeof(in)); while(m--) { scanf("%d %d",&a,&b); if(map[a][b]==0) { map[a][b]=1; in[b]+;//記録入度 } } int num=0; while(num!=n) { for(int i=1;i<=n;i++) { if(in[i]==0)/削除度0の点とその辺 { in[i]=-1; ans[num+]=i;//この点を記録する t=i;//ポイントを保存し、そのポイントに接続されているエッジを削除します break; } } for(int i=1;i<=n;i++) { if(map[t][i]==1) in[i]--//削除した点に接続されたエッジの入度から1を減算 } } for(int i=0;i { printf(i==n-1?"%d":"%d ",ans[i]); } } return 0; }
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others) Total Submission(s): 24346 Accepted Submission(s): 9798
Problem Description
Nチーム(1<=N<=500)があり、番号は1、2、3、...Nは試合を行い、試合が終わった後、審判委員会はすべての参加チームを行った後から順番に順位をつけなければならないが、現在、審判委員会は直接各チームの試合成績を得ることができず、各試合の結果、すなわちP 1がP 2に勝ったことしか知らず、P 1,P 2で表され、順位はP 1がP 2の前にある.今、プログラムを作ってランキングを確定してください.
Input
入力にはいくつかのグループがあり、各グループの第1の動作の2つの数N(1<=N<=500)、M;ここで、Nは行列の個数を表し、MはM行に続く入力データを表す.次のM行データでは、行ごとに2つの整数P 1があり、P 2はP 1チームがP 2チームに勝ったことを示す.
Output
要件に合致するランキングを与えます.出力時にキュー番号の間にスペースがあり、最後の名前の後ろにスペースがありません.
その他の説明:条件に合致する順位は唯一ではない可能性があります.この場合、出力時の番号の小さいチームが上位にあることが要求されます.入力データは正しいことを保証します.すなわち、入力データは必ず要求に合致するランキングを確保します.
Sample Input
4 3 1 2 2 3 4 3
Sample Output
1 2 4 3
既にAC済みのコード:
#include #include #include using namespace std; int main() { int map[550][550],in[2100],ans[2100]; int n,m,a,b,t; while(scanf("%d %d",&n,&m)!=EOF) { memset(map,0,sizeof(map)); memset(in,0,sizeof(in)); while(m--) { scanf("%d %d",&a,&b); if(map[a][b]==0) { map[a][b]=1; in[b]+;//記録入度 } } int num=0; while(num!=n) { for(int i=1;i<=n;i++) { if(in[i]==0)/削除度0の点とその辺 { in[i]=-1; ans[num+]=i;//この点を記録する t=i;//ポイントを保存し、そのポイントに接続されているエッジを削除します break; } } for(int i=1;i<=n;i++) { if(map[t][i]==1) in[i]--//削除した点に接続されたエッジの入度から1を減算 } } for(int i=0;i { printf(i==n-1?"%d":"%d ",ans[i]); } } return 0; }