반응형
https://www.acmicpc.net/problem/10971
10971번: 외판원 순회 2
첫째 줄에 도시의 수 N이 주어진다. (2 ≤ N ≤ 10) 다음 N개의 줄에는 비용 행렬이 주어진다. 각 행렬의 성분은 1,000,000 이하의 양의 정수이며, 갈 수 없는 경우는 0이 주어진다. W[i][j]는 도시 i에서 j
www.acmicpc.net
1. 문제설명
외판원 순회 문제입니다.
시작점을 정해주지 않았기 때문에 모든 노드에서 시작할 수 있습니다.
우선순위큐를 이용해서 최단거리를 우선으로 방문해야 메모리와 시간을 아낄 수 있습니다.
시험삼아 우선순위큐만 큐로 바꿔서 돌려봤습니다.
메모리 63072KB, 360ms 걸린 게 일반 큐를 이용한 것이고
메모리 2500KB, 4ms가 우선순위 큐를 이용한 것입니다.
메모리와 시간차이가 나는 이유는
우선순위큐를 이용할 때는 최단거리를 우선으로 방문하고 그 이외에는 방문하지 않는데
큐를 이용할 때는 이미 방문했던 점이 최단거리가 아닐 수 있기 때문에
계속해서 해당 노드의 해당 상태에 대해 불필요한 계산이 이루어져서
시간과 메모리가 많이 사용됩니다.
2.문제풀이코드 C++
#include <bits/stdc++.h>
int ch[11][1 << 11];
int n, arr[11][11];
struct Node {
int cur, vis, st, dist;
bool operator<(const Node& b) const {
return dist > b.dist;
}
};
using namespace std;
int main() {
priority_queue<Node> Q;
cin >> n;
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
cin >> arr[i][j];
}
Q.push({ i,1 << i,i ,0 });
}
int ans = INT_MAX;
while (!Q.empty()) {
int cur = Q.top().cur;
int vis = Q.top().vis;
int st = Q.top().st;
int dist = Q.top().dist;
Q.pop();
ch[cur][vis] = 1;
if (vis == (1 << n) - 1) {
if (arr[cur][st] != 0) ans = min(ans, dist + arr[cur][st]);
}
for (int i = 0; i < n; i++) {
if (arr[cur][i] > 0 && ch[cur][vis | (1 << i)] == 0) {
Q.push({ i,vis | (1 << i),st,dist + arr[cur][i] });
}
}
}
cout << ans << '\n';
return 0;
}
반응형
'Algorithm > problem' 카테고리의 다른 글
백준 2294번 : 동전 2 - dp C++ (0) | 2022.03.05 |
---|---|
백준 14499번 : 주사위 굴리기 (0) | 2022.03.05 |
백준 3780번 : 네트워크 연결 - Union&Find dis-joint set C++ (0) | 2022.03.03 |
백준 17398번 : 통신망 분할 - Union & Find dis-joint set 알고리즘 C++ (0) | 2022.03.02 |
백준 15459번 : Haybale Feast - Union&Find dis-joint set C++ 문제풀이 (0) | 2022.03.02 |