※ 글쓴이는 취미로 코딩을 익혀보는 사람이라 정확하지 않은 내용을 담고 있을 수 있다 ※
이번에 볼 문제는 백준 3075번 문제인 Astromeeting이다.
문제는 아래 링크를 확인하자.
https://www.acmicpc.net/problem/3075
3075번: Astromeeting
때는 아주 먼 미래, 지구인은 태양계를 넘어 은하계를 넘나들 수 있는 시대를 맞이하게 되었다. ㈜유료도로당이라는 회사는 은하간에 초광속터널을 제공하여 은하간에 편리하고 빠르게 이동할
www.acmicpc.net
문제에 따르면 은하 A에서 B까지 이동하는 데에 드는 최소비용은 두 은하 사이의 최단거리의 제곱과 같다.
두 은하 사이의 최단거리는 dijkstra 알고리즘 등을 이용해 간단히 구할 수 있으므로, dijkstra를 n번 돌려 각 사람들로부터 각 은하에 도달하는 비용들을 구하고 이들을 누적해 각 테스트케이스의 답을 구하자. n이 클 경우 floyd-warshall이 더 효율적일 수 있으나 주어지는 입력의 크기가 매우 작으므로 무엇을 사용해도 상관없을 것이다.
n명의 사람들이 항상 만날 수 있는 입력만 주어지지만, n명의 사람들이 방문할 수 없는 은하가 입력에 존재할 수는 있다. 해당 은하를 답의 후보로 생각하지 않도록 구현에 유의하자. 글쓴이는 그런 은하의 경우 거리를 무한대(아래 구현에서는 1,000,000,000,000,000,007)로 취급해주었다.
또한 각 은하에 도달하는 비용의 누적값은 32비트 정수 자료형으로 저장하지 못하는 큰 수가 나올 수 있음에 유의하자.
아래는 제출한 소스코드이다.
#include <iostream>
#include <vector>
#include <queue>
#include <cstring>
using namespace std;
typedef long long ll;
int T, P;
vector<pair<int, int>> G[101];
priority_queue<pair<int, int>> pq;
ll total[101];
void dijkstra(int x) {
vector<int> dist(P + 1);
dist[x] = 1;
pq.push(make_pair(-1, x));
while (!pq.empty()) {
int d = -pq.top().first, cur = pq.top().second; pq.pop();
if (dist[cur] < d) continue;
for (auto& p : G[cur]) {
int nxt = p.first, dd = p.second;
if (!dist[nxt] || d + dd < dist[nxt]) {
dist[nxt] = d + dd;
pq.push(make_pair(-(d + dd), nxt));
}
}
}
for (int i = 1; i <= P; i++) {
if (dist[i]) total[i] += (dist[i] - 1) * (dist[i] - 1);
else total[i] = 1000000000000000007LL;
}
}
int main() {
ios::sync_with_stdio(0);
cin.tie(0);
cin >> T;
while (T--) {
int N, Q; cin >> N >> P >> Q;
for (int i = 1; i <= P; i++) G[i].clear(), total[i] = 0;
vector<int> pp(N);
for (int i = 0; i < N; i++) cin >> pp[i];
while (Q--) {
int x, y, d; cin >> x >> y >> d;
G[x].emplace_back(make_pair(y, d));
G[y].emplace_back(make_pair(x, d));
}
for (auto& x : pp) dijkstra(x);
int ans = -1; ll ansd = 1000000000000000006LL;
for (int i = 1; i <= P; i++) {
if (total[i] < ansd) ansd = total[i], ans = i;
}
cout << ans << ' ' << ansd << '\n';
}
}
'BOJ' 카테고리의 다른 글
[BOJ 2624 // C++] 동전 바꿔주기 (1) | 2023.12.31 |
---|---|
[BOJ 3077 // C++] 임진왜란 (0) | 2023.12.30 |
[BOJ 3061 // C++] 사다리 (0) | 2023.12.28 |
[BOJ 3340 // C++] Multi-key Sorting (0) | 2023.12.27 |
[BOJ 2942 // C++] 퍼거슨과 사과 (1) | 2023.12.26 |