https://www.acmicpc.net/problem/1238
1238번: 파티
첫째 줄에 N(1 ≤ N ≤ 1,000), M(1 ≤ M ≤ 10,000), X가 공백으로 구분되어 입력된다. 두 번째 줄부터 M+1번째 줄까지 i번째 도로의 시작점, 끝점, 그리고 이 도로를 지나는데 필요한 소요시간 Ti가 들어
www.acmicpc.net
문제해석
예를 들어 n=4 ,x=2 인 경우를 생각해보자
1->2 + 2->1
2->2 + 2->2 (시작점 끝점이 같은경우는 없음)
3->2 + 2->3
4->2 + 4->1 이 세가지 경우 중에 가장 작은 값이 답이 된다.
따라서 각 마을에서 마을까지 전부 다익스트라를 돌리든 플로이드를 돌리든 최단 거리를 저장시켜놔야한다고 생각했다.
마을개수가 최대 1000이므로 플로이드를 사용하여 구현하면 1000*1000*1000=10억 이므로 시간 초과가 날것 같아서 그렇게 하는건 포기했고 전부 다익스트라를 돌려서 풀어보기로 했다.
전부 다익스트라를 돌려볼거니까 d배열을 2차원으로 수정하고 그 외 자잘한 부분을 수정한거 빼고 저번에 작성한 다익스트라 코드를 거의 그대로 사용하였다.
전부 다익스트라를 돌린 후에 d[i][j]는 i마을에서 j마을까지 최단거리가 저장되어있을것이다.
그 중 x마을로 갔다가 돌아오는 거리가 가장 짧은 것을 답으로 출력하면 끝
코드
#include <iostream>
#include <algorithm>
#include <vector>
#include <queue>
#include <string.h>
#define INF 999999999
using namespace std;
int getsmall();
void dijk(int start);
void reset();
priority_queue < pair<int,int> , vector< pair<int,int> > , greater< pair<int,int> > >pq;
vector < pair<int,int> > v[1001];
int d[1001][1001];
bool visited[1001];
int n,m,x;
int main(){
cout.tie(NULL);
cin.tie(NULL);
ios_base::sync_with_stdio(false);
cin>>n>>m>>x;
for(int i=0; i<m; i++)
{
int s,e,t;
cin>>s>>e>>t;
v[s].push_back({t,e});
}
for(int i=1; i<=n; i++)
{
reset();
dijk(i);
}
int ans=0;
for(int i=1; i<=n; i++)
{
ans=max(d[i][x]+d[x][i],ans);
}
cout<<ans;
}
void dijk(int start){
for(int i=1; i<=n; i++)
{
d[start][i]=INF;
}
d[start][start]=0;
for(int i=0; i<v[start].size(); i++)
{
d[start][v[start][i].second]=v[start][i].first;
pq.push({v[start][i].first,v[start][i].second});
}
visited[start]=1;
for(int j=0; j<n; j++)
{
int cur=getsmall();
visited[cur]=1;
for(int i=0; i<v[cur].size(); i++)
{
if(visited[v[cur][i].second]==0&&d[start][cur]+v[cur][i].first<d[start][v[cur][i].second])
{
d[start][v[cur][i].second]=d[start][cur]+v[cur][i].first;
pq.push({d[start][v[cur][i].second],v[cur][i].second});
}
}
}
}
int getsmall(){
int index=0;
while(!pq.empty())
{
index=pq.top().second;
pq.pop();
if(visited[index]==0)
{
return index;
}
}
return index;
}
void reset(){
pq=priority_queue < pair<int,int> , vector< pair<int,int> > , greater< pair<int,int> > >();
memset(visited,0,sizeof(visited));
}
'백준문제풀이' 카테고리의 다른 글
백준 문제 1405번 미친 로봇 문제풀이 c++ (0) | 2022.03.22 |
---|---|
백준 문제 1016번 제곱 ㄴㄴ 수 문제풀이 c++ (0) | 2022.03.22 |
백준 문제 1753번 최단경로 문제풀이 c++ (0) | 2022.03.22 |
백준 문제 14425번 문자열 집합 문제풀이 c++ (0) | 2022.03.22 |
백준 문제 5052번 전화번호 목록 문제풀이 c++ (0) | 2022.03.22 |