Computer >> 컴퓨터 >  >> 프로그래밍 >> Python

Python으로 도시 네트워크의 최대 랭크(Maximal Network Rank) 구하기

n개의 도시가 있고, 이 도시들을 연결하는 여러 개의 도로가 있다고 가정해 보겠습니다. 각 roads[i] = [u, v]는 도시 u와 도시 v 사이에 양방향 도로가 존재함을 의미합니다.

여기서 네트워크 랭크(network rank)란 두 도시 중 하나에 직접 연결된 도로의 총 개수를 말합니다. 단, 하나의 도로가 두 도시 모두에 직접 연결되어 있는 경우에는 한 번만 계산합니다. 그리고 최대 네트워크 랭크(maximal network rank)는 서로 다른 도시 쌍들 중에서 가장 큰 네트워크 랭크 값을 의미합니다.

예를 들어 다음과 같은 입력이 주어졌을 때,

Python으로 도시 네트워크의 최대 랭크(Maximal Network Rank) 구하기

출력은 5가 됩니다. 도시 1과 도시 2를 기준으로 직접 연결된 도로를 합산하면 총 5개이기 때문입니다.

해결 접근 방법

이 문제를 해결하기 위해 다음과 같은 단계를 따릅니다.

  • n := 노드(도시)의 개수
  • s := 새로운 집합(set) 생성
  • d := 딕셔너리(맵) 생성, 키가 없으면 기본값 0 반환
  • roads의 각 간선 (x, y)에 대해:
    • d[x] := d[x] + 1
    • d[y] := d[y] + 1
    • 집합 s에 쌍 (x, y) 삽입
  • ans := 0으로 초기화
  • l := 0부터 n까지의 리스트 생성
  • l을 노드별 차수(degree)를 기준으로 내림차순 정렬
  • threshold := d[l[0]]과 d[l[1]] 중 최솟값
  • i를 0부터 l의 크기 - 1까지 반복:
    • j를 i+1부터 l의 크기 - 1까지 반복:
      • 만약 d[l[j]] < threshold라면 내부 반복문 종료
      • curr := d[l[i]] + d[l[j]]
      • (l[i], l[j]) 또는 (l[j], l[i])가 집합 s에 존재하면 curr에서 1 감소
      • ans := ans와 curr 중 최댓값
  • ans 반환

구현 예제

아래 파이썬 코드를 통해 더 자세히 이해해 보겠습니다.

from collections import defaultdict
def solve(roads):
   nodes = set()
   s = set()
   d = defaultdict(int)
   for x,y in roads:
      nodes.update([x,y])
      d[x]+=1
      d[y]+=1
      s.add((x,y))

   ans = 0
   n = len(nodes)
   l = list(range(n))
   l.sort(key=lambda x:d[x], reverse = True)
   threshold = min(d[l[0]],d[l[1]])
   for i in range(len(l)-1):
      for j in range(i+1,len(l)):
         if d[l[j]]<threshold:
            break
      curr = d[l[i]]+d[l[j]]
      if (l[i],l[j]) in s or (l[j],l[i]) in s:
         curr-=1
      ans = max(ans,curr)
   return ans

roads = [(0,1),(0,3),(1,2),(1,3),(2,3),(2,4)]
print(solve(roads))

입력

[(0,1),(0,3),(1,2),(1,3),(2,3),(2,4)]

출력

5

코드 설명

이 알고리즘은 먼저 각 도시의 차수(연결된 도로 수)를 계산한 후, 차수가 높은 도시부터 내림차순으로 정렬합니다. 그다음 상위 두 도시의 차수 합을 임계값(threshold)으로 설정하여, 임계값보다 작은 차수를 가진 도시 조합은 미리 탐색을 중단함으로써 불필요한 연산을 줄입니다. 두 도시가 서로 직접 연결되어 있는 경우에는 해당 도로가 중복 계산되므로 1을 빼주어 정확한 네트워크 랭크를 구합니다. 이러한 최적화 덕분에 모든 도시 쌍을 완전 탐색하는 것보다 효율적으로 최대 네트워크 랭크를 찾을 수 있습니다.