結果
問題 | No.517 壊れたアクセサリー |
ユーザー |
👑 ![]() |
提出日時 | 2021-02-10 05:14:05 |
言語 | PyPy3 (7.3.15) |
結果 |
AC
|
実行時間 | 65 ms / 2,000 ms |
コード長 | 6,958 bytes |
コンパイル時間 | 368 ms |
コンパイル使用メモリ | 81,920 KB |
実行使用メモリ | 69,760 KB |
最終ジャッジ日時 | 2024-07-07 14:04:40 |
合計ジャッジ時間 | 2,514 ms |
ジャッジサーバーID (参考情報) |
judge1 / judge4 |
(要ログイン)
ファイルパターン | 結果 |
---|---|
sample | AC * 4 |
other | AC * 15 |
ソースコード
class Digraph:"""重み[なし]有向グラフを生成する."""#入力定義def __init__(self,vertex=[]):self.vertex=set(vertex)self.edge_number=0self.vertex_number=len(vertex)self.adjacent_out={v:set() for v in vertex} #出近傍(vが始点)self.adjacent_in={v:set() for v in vertex} #入近傍(vが終点)#頂点の追加def add_vertex(self,*adder):for v in adder:if not self.vertex_exist(v):self.adjacent_in[v]=set()self.adjacent_out[v]=set()self.vertex.add(v)self.vertex_number+=1#辺の追加def add_edge(self,From,To):self.add_vertex(From)self.add_vertex(To)if To not in self.adjacent_out[From]:self.adjacent_out[From].add(To)self.adjacent_in[To].add(From)self.edge_number+=1#辺を除くdef remove_edge(self,From,To):self.add_vertex(From)self.add_vertex(To)if To in self.adjacent_out[From]:self.adjacent_out[From].discard(To)self.adjacent_in[To].discard(From)self.edge_number-=1#頂点を除くdef remove_vertex(self,*vertexes):for v in vertexes:if v in self.vertex:self.vertex_number-=1for u in self.adjacent_out[v]:self.adjacent_in[u].discard(v)self.edge_number-=1del self.adjacent_out[v]for u in self.adjacent_in[v]:self.adjacent_out[u].discard(v)self.edge_number-=1del self.adjacent_in[v]self.vertex.discard(v)#Walkの追加def add_walk(self,*walk):N=len(walk)for k in range(N-1):self.add_edge(walk[k],walk[k+1])#Cycleの追加def add_cycle(self,*cycle):self.add_walk(*cycle)self.add_edge(cycle[-1],cycle[0])#頂点の交換def __vertex_swap(self,p,q):self.vertex.sort()#グラフに頂点が存在するか否かdef vertex_exist(self,v):return v in self.vertex#グラフに辺が存在するか否かdef edge_exist(self,From,To):if self.vertex_exist(From) and self.vertex_exist(To):return Falsereturn To in self.adjacent_out[From]#近傍def neighbohood(self,v):"""vの出近傍, 入近傍を出力する.Input:v:頂点Output:(出近傍, 入近傍)"""if not self.vertex_exist(v):return (set(),set())return (self.adjacent_out[v],self.adjacent_in[v])#出次数def out_degree(self,v):if not self.vertex_exist(v):return 0return len(self.adjacent_out[v])#入次数def in_degree(self,v):if not self.vertex_exist(v):return 0return len(self.adjacent_in[v])#次数def degree(self,v):return (self.out_degree(v),self.in_degree(v))#頂点数def vertex_count(self):return self.vertex_number#辺数def edge_count(self):return self.edge_number#頂点vに到達可能な頂点def reachable_to(self,v):if not self.vertex_exist(v):return []from collections import dequeT={v:0 for v in self.vertex}T[v]=1Q=deque([v])while Q:x=Q.popleft()for y in self.adjacent_in[x]:if not T[y]:T[y]=1Q.append(y)return [x for x in self.vertex if T[x]]#頂点vから到達可能な頂点def reachable_from(self,v):if not self.vertex_exist(v):return []from collections import dequeT={v:0 for v in self.vertex}T[v]=1Q=deque([v])while Q:x=Q.popleft()for y in self.adjacent_out[x]:if not T[y]:T[y]=1Q.append(y)return [x for x in self.vertex if T[x]]#深いコピーdef deepcopy(self):from copy import deepcopyD=Digraph()D.vertex=deepcopy(self.vertex)D.edge_number=self.edge_numberD.vertex_number=len(self.vertex)D.adjacent_out=deepcopy(self.adjacent_out)D.adjacent_in=deepcopy(self.adjacent_in)return D#Warshall–Floyddef Warshall_Floyd(D):"""Warshall–Floyd法を用いて,全点間距離を求める.D:負Cycleを含まない有向グラフ"""T={v:{} for v in D.vertex} #T[u][v]:uからvへfor u in D.vertex:for v in D.vertex:if v==u:T[u][v]=0elif v in D.adjacent_out[u]:T[u][v]=1else:T[u][v]=float("inf")for u in D.vertex:for v in D.vertex:for w in D.vertex:T[v][w]=min(T[v][w],T[v][u]+T[u][w])return Tdef Dijkstra(D,From,To,with_path=False):"""Dijksta法を用いて,FromからToまでの距離を求める.D:辺の重みが全て非負の有向グラフFrom:始点To:終点with_path:最短路も含めて出力するか?(出力の結果)with_path=True->(距離,最短経路の辿る際の前の頂点)with_path=False->距離"""from copy import copyfrom heapq import heappush,heappopT={v:float("inf") for v in D.vertex}T[From]=0if with_path:Prev={v:None for v in D.vertex}Q=[(0,From)]Flag=Falsewhile Q:c,u=heappop(Q)if u==To:Flag=Truebreakif T[u]<c:continuefor v in D.adjacent_out[u]:if T[v]>T[u]+1:T[v]=T[u]+1heappush(Q,(T[v],v))if with_path:Prev[v]=uif not Flag:if with_path:return (float("inf"),None)else:return float("inf")if with_path:path=[To]u=Towhile (Prev[u]!=None):u=Prev[u]path.append(u)return (T[To],path[::-1])else:return T[To]#================================================S=""N=int(input())A=[]for _ in range(N):A.append(input())S+=A[-1]M=int(input())B=[]for _ in range(M):B.append(input())D=Digraph(S)for alpha in A:for i in range(len(alpha)-1):D.add_edge(alpha[i],alpha[i+1])for beta in B:for j in range(len(beta)-1):D.add_edge(beta[j],beta[j+1])X=Warshall_Floyd(D)flag=0for s in S:for t in S:if X[s][t]==len(S)-1:flag+=1i,j=s,tif flag!=1:print(-1)exit()_,A=Dijkstra(D,i,j,True)print("".join(A))