문제 : http://acmicpc.net/proble/1916


해당 문제는 다익스트라 알고리즘을 이용해서 구해야하는 방법이다.


다익스트라에 대한 설명은 해당 링크를 참조해주시기를 바랍니다.


여기서는 우선순위 큐를 이용해서 다익스트라 알고리즘을 구현하였습니다. 


우선순위 큐는 큐의 최소값이 가장 우선되면서 pop이 됩니다.


그렇기 때문에 해당 알고리즘은 값을 넣을때 음수로 저장하고 다시 꺼낼때도 음수로 나오게 됩니다.


값의 저장  pq.push(make_pair(-neighbor_dist, neighbor));


값의 이용 int cost = -pq.top().first;



// ConsoleApplication2.cpp : 콘솔 응용 프로그램에 대한 진입점을 정의합니다. // #include <iostream> #include <cstdio> #include <queue> #include <vector> #include <algorithm> //필요는 없으나 습관 #include <limits.h> //INT_MAX 값을 불러오기 위함. #define NODE_MAX 1001 using namespace std; typedef pair<int, int> pii; int n, m; vector<pii> graph[NODE_MAX]; vector<int> dijkstra(int start) { //자기 자신을 가리키면 비용은 0 vector<int> dist(n, INT_MAX); dist[start] = 0; /* 시작할때 cost의 가중치가 없어야하고 어느 노드에 대해서 값을 구할 것인지 결정해야함 그래서 파라미터 0, start 들어감. */ priority_queue<pii> pq; pq.push(make_pair(0, start)); while (!pq.empty()) { /* 우선순위 큐에서 가장 작은 값이 가장 먼저 나오기 때문에 음수로 저장하고 꺼낼때 음수를 사용한다. */ int cost = -pq.top().first; // 현재 노드까지의 가중치값 int cur_vertex = pq.top().second; // 현재 노드 pq.pop(); /* 새로운 cost의 가중치가 기존 가중치보다 크다면 생략. */ if (dist[cur_vertex] < cost) continue; /* cur_vertex 노드와 인접 노드간의 가중치를 모두 구하기 위함. */ for (int i = 0; i < graph[cur_vertex].size(); i++) { /* neighbor = 인접 노드 neighbor_dist = 이전 노드까지의 가중치 최소값을 뜻하는 cost + 현재 인접노드[i] 가중치를 더한 값. */ int neighbor = graph[cur_vertex][i].first; int neighbor_dist = cost + graph[cur_vertex][i].second; /* 기존에 저장된 인접노드까지의 가중치가 클 경우 새롭게 갱신 */ if (dist[neighbor] > neighbor_dist) { dist[neighbor] = neighbor_dist; // 갱신. pq.push(make_pair(-neighbor_dist, neighbor)); //우선순위큐이기 때문에 가중치 값을 음수로 저장. } } } return dist; } int main(void) { cin >> n >> m; n++; // 값의 시작은 1부터이기 때문에. for (int i = 0; i < m; i++) { int from, to, val; cin >> from >> to >> val; graph[from].push_back(make_pair(to, val)); } int from, to; cin >> from >> to; //시작점 from에서 갈 수 있는 모든 노드의 가중치 값을 result에 저장하고 목적지 to의 값을 불러옴. vector<int> result(dijkstra(from)); cout << result[to] << endl; return 0; }





1697 - 숨바꼭질 https://www.acmicpc.net/problem/1697


문제 분류에서는 DFS라고 나와있는데, 사실상 알고보면 BFS 문제다.


아무 것도 모르던 나에게 DFS라고 하길래 노가다 하면서 계속 고민을 해봤는데 이거는 ㄹㅇ 암만 봐도 노답이었다. BFS 쓰자.


BFS를 잘 모르겠다면 체스 나이트 최단거리 구하는 문제부터 연습하자

9466 - 텀 프로젝트 https://www.acmicpc.net/problem/9466


기존의 흔히 사용하는 DFS는 2차원 배열에서 값을 찾는 것이지만,


해당 문제는 1차원 배열에서 문제를 찾는 방식임.


1. 이미 방문한 곳은 방문하지 않도록 하기 위해서 visit1을 선언했다.
그냥 한번이라도 들리게 된다면 visit1의 값을 1로 변경했다.
그렇기 때문에 visit1의 값이 0일때만 깊이를 파고들도록 한다.

2. 순회의 끝을 찾기 위해서 visit2를 사용했다.
깊이를 들어갈 때마다 visit2의 값을 1로 변경했다.
그러다가 다음에 나올 visit2의 값이 만약에 0이라면 순회의 끝에 도달했다고 볼 수 있다.
그렇기 때문에 사이클을 돌려서 얼마만큼의 깊이까지 들어갔는지 체크를 하도록 한다.

#include<stdio.h> #include<string.h> #include<stdlib.h> int map[100001]; int visit1[100001]; //map에서 한번이라도 체크되었는지 확인. int visit2[100001]; //순회의 끝을 찾기 위함. int total, visit_count=0; void dfs(int i) { int a; int next = map[i]; visit1[i] = 1; //printf("visit1[%d] : %d, visit_count: %d\n", i, map[i], visit_count); if(visit1[next] == 0) { dfs(next); } else { if(visit2[next] == 0) { for(a=next; a!=i; a=map[a]) { visit_count++; //printf("i : %d, a: %d, map[%d] : %d, visit_count : %d\n", i, a, a, map[a], visit_count); } visit_count++; } } visit2[i] = 1; } int main(void) { int i, total_count = 0, non_visit_count =0, n; scanf("%d", &total); fflush(stdin); while(total_count++ <total) { memset(map, 0, sizeof(map)); memset(visit1, 0, sizeof(visit1)); memset(visit2, 0, sizeof(visit2)); scanf("%d", &n); for(i=1; i<=n; i++) { scanf("%d", &map[i]); } fflush(stdin); visit_count = 0; for(i=1; i<=n; i++) { if(visit1[i] == 0) { dfs(i); } } printf("%d\n", n-visit_count); } return 0; }



2667-단지번호붙이기 acmicpc.net/problem/2667


해당 문제는 DFS 기초문제이다.


DFS를 사용한 이후에 나온 값들에 대한 정렬이 필요하다.


나는 처음에 퀵정렬 사용하려고 qsort함수를 사용하기 위해서 int compare(const void* a, const void* b) 함수를 새로 만들어서 사용하기도 했는데


왜인지 잘 모르겠지만 정렬이 잘 안됬음.


그래서 그냥 버블정령 만들어서 바로 사용했음.


#include<stdio.h> #include<string.h> #include<stdlib.h> int map[100][100]; int visit[100][100]; int* result; int stack=0; int n; int max=0; void dfs(int i, int j) { int x, y,k; int dx[] = {0,1,0,-1}; int dy[] = {1,0,-1,0}; visit[i][j] = 1; max++; for(k=0; k<4; k++) { x=i+dx[k]; y=j+dy[k]; if(x<0 || y<0 || x>n-1 || y>n-1) continue; if(visit[x][y] == 0 && map[i][j] == map[x][y]) { dfs(x, y); } } } int main(void) { int i, j; char input[100]; int temp; scanf("%d", &n); fflush(stdin); result = (int*)malloc(sizeof(int)*n*n); memset(map, 0, sizeof(map)); memset(visit, 0, sizeof(visit)); memset(result, 0, sizeof(result)); for(i=0; i<n; i++) { scanf("%s", input); fflush(stdin); for(j=0; j<n; j++) { map[i][j] = input[j]-48; } } for(i=0; i<n; i++) { for(j=0; j<n; j++) { if(visit[i][j] == 0 && map[i][j] == 1) { max=0; dfs(i, j); result[stack++] = max; } } } for(i=0; i<stack-1; i++) { for(j=0; j<stack-1; j++) { if(result[j] > result[j+1]) { temp = result[j]; result[j] = result[j+1]; result[j+1] = temp; } } } printf("%d\n", stack); for(i=0; i<stack; i++) { printf("%d\n", result[i]); } return 0; }


10026-적록색약 acmicpc.net/problem/10026


DFS를 활용한 기초문제


dfs함수 안에서 조건문의 값 크기를 잘 설정하자.


저기서 x, y 조건을 약간 잘못걸어서 에러를 찾지 못하고 오래동안 헤맸음.

#include<stdio.h> #include<string.h> #include<stdlib.h> int arr[1000][1000]; int visit[1000][1000]; int result = 0; int n = 0; void dfs(int i, int j) { int x,y,k; int dx[4] = {0,1,0,-1}; int dy[4] = {1,0,-1,0}; for(k=0; k<4; k++) { x = i + dx[k]; y = j + dy[k]; if( x<0 || y<0 || x>n-1 || y>n-1) continue; if(visit[x][y] == 0 && arr[i][j] == arr[x][y]) { //printf("Log i,j,x,y : %d %d %d %d\n", i,j,x,y); //printf("Log 좌표값 : %d %d\n", arr[i][j], arr[x][y]); //printf("Log visit값 : %d %d\n\n\n", visit[i][j], visit[x][y]); visit[x][y] = 1; dfs(x,y); } } } int main(void) { int i, j; char str[1000]; memset(visit,0,sizeof(visit)); memset(arr,0,sizeof(arr)); scanf("%d", &n); fflush(stdin); for(i=0; i<n; i++) { scanf("%s", str); fflush(stdin); for(j=0; j<n; j++) { if(str[j] == 'R') { arr[i][j] = 2; } else if(str[j] == 'B') { arr[i][j] = 1; } } } //일반인 for(i=0; i<n; i++) { for(j=0; j<n; j++) { if(visit[i][j] == 0) { dfs(i, j); result ++; } } } printf("%d ", result); //장애인 memset(visit,0,sizeof(visit)); for(i=0; i<n; i++) { for(j=0; j<n; j++) { if(arr[i][j] == 2) { arr[i][j] = 0; } } } result = 0; for(i=0; i<n; i++) { for(j=0; j<n; j++) { if(visit[i][j] == 0) { visit[i][j] = 1; dfs(i, j); result ++; } } } printf("%d\n", result); return 0; }



+ Recent posts