atcoder ABC D - Restricted Permutationの勉強
問題:
atcoder.jp
参考:https://qiita.com/sano192/items/c301aa0f8c5680eea429
https://zenn.dev/fjnkt98/articles/c9b21e90150e7b
・前提知識:トポロジカルソートについて知っている(アルゴ式などを参考)。dfsについても(けんちょんさんのqiitaの記事などくを参考)。
・考え方:トポロジカルソートを使うのだがトポロジカルソートは一意に決まらないので、その中の辞書順で一番はじめのものを出力するのがこの問題。これはBFS的に実装する必要があり、有向辺がない頂点をBFSで求めていくことになる。
import heapq #ヒープの中にある最小値を取り出すため。 n,m=map(int,input().split()) cnt=[0 for _ in range(n)] #ある頂点に向いている有向辺の数をいれる。 G=[[] for _ in range(n)] for i in range(m): a,b=map(int,input().split()) a-=1 b-=1 G[a].append(b) cnt[b]+=1 #頂点bに向いている有向辺の座標を+1。 que=[] #向いている辺がない頂点をいれる。 for i in range(n): if cnt[i]==0: que.append(i) #リストをヒープにする heapq.heapify(que) #答えを入れるリスト ans=[] #キューが空になるまで while len(que)!=0: #queの一番小さい値をvとする。 v=heapq.heappop(que) ans.append(v) #vから行ける点をnvとする。 for nv in G[v]: cnt[nv]-=1 #vの頂点とvからの辺と消す。つまりnvへと向かう辺の数cnt[nv]は-1になる。 if cnt[nv]==0: heapq.heappush(que,nv) #queにnvを入れる。 if len(ans)!=n: print(-1) else: for i in range(n): print(ans[i]+1,end=' ') #頂点を0からにしているので