개발/algorithm
[백준 1647번] 도시 분할 계획- python / 크루스칼 알고리즘
zzi_on2
2022. 4. 26. 14:42
문제 링크
풀이
- 크루스칼 알고리즘을 사용해서 모든 정점을 잇는 최소 비용을 구한 후 가장 큰 값을 빼줘서 두 도시로 나눌 수 있다.
set을 사용해서 구현하니 시간 초과가 발생하였다.
# 시간 초과 발생
import sys
input = sys.stdin.readline
n, m = map(int,input().split())
cost = []
for _ in range(m):
a, b, c = map(int,input().split())
cost.append([a,b,c])
cost.sort(key = lambda x : x[2])
connect = set([cost[0][0], cost[0][1]])
answer = []
answer.append(cost[0][2])
while len(connect) < n :
for c in cost:
if c[0] in connect and c[1] in connect :
continue
if c[0] in connect or c[1] in connect :
connect.update([c[0],c[1]])
answer.append(c[2])
break
print(sum(answer[:-1]))
- 유니온 파인드 함수로 변경해서 구현하니 통과
# https://www.acmicpc.net/problem/1647
import sys
input = sys.stdin.readline
# 부모 찾는 함수
def find(x):
if x == parent[x]:
return x
parent[x] = find(parent[x])
return parent[x]
# 두 집합 합치는 함수
def union(a,b):
a = parent[a]
b = parent[b]
if a == b:
return
if a < b:
parent[b] = a
else:
parent[a] = b
n, m = map(int,input().split())
# 부모 저장 테이블
parent = [0] * (n+1)
# 자기 자신으로 초기화
for i in range(1,n+1):
parent[i] = i
edges = []
for _ in range(m):
a, b, cost = map(int,input().split())
edges.append([cost,a,b])
# cost 기준 정렬
edges.sort()
# 연결 비용 저장
answer = []
for edge in edges:
cost, a, b = edge
# 같은 집합에 속하지 않으면
if find(a) != find(b):
# 연결하고 비용 더하기
union(a,b)
answer.append(cost)
# 가장 큰 비용 제거
print(sum(answer[:-1]))