[백준 16234번 C/C++] 인구 이동
[백준 16234번 C/C++] 인구 이동

https://www.acmicpc.net/problem/16234
16234번: 인구 이동
N×N크기의 땅이 있고, 땅은 1×1개의 칸으로 나누어져 있다. 각각의 땅에는 나라가 하나씩 존재하며, r행 c열에 있는 나라에는 A[r][c]명이 살고 있다. 인접한 나라 사이에는 국경선이 존재한다. 모
www.acmicpc.net
해결전략
너비 우선 탐색 BFS
코드
#include <iostream> #include <queue> #include <vector> #include <algorithm> #include <cstring> using namespace std; const int dy[4] = {-1, 1, 0, 0}; // 선언: 상, 하 이동 const int dx[4] = {0, 0, -1, 1}; // 선언: 좌, 우 이동 int n, l, r; // 선언: n - 격자 크기, l - 최소 인구 차이, r - 최대 인구 차이 int a[50][50]; // 선언: 각 나라의 인구 수 행렬 bool visit[50][50]; // 선언: 각 나라의 방문 여부 행렬 vector<pair<int, int>> open; // 선언: 연합국 위치 저장 // bfs 함수: 인구 이동이 가능한 인접한 나라를 찾는 함수 bool bfs(int y, int x) { if (visit[y][x]) return false; // 이미 방문한 나라라면 false 반환 open.clear(); // 연합국 위치 저장 벡터 초기화 queue<pair<int, int>> q; // 선언: 연합국 위치 저장 큐 q.push(make_pair(y, x)); // 해당 위치를 큐에 추가 visit[y][x] = true; // 그 위치를 방문 표시 open.push_back(make_pair(y, x)); // 연합국 위치 저장 벡터에 추가 while (!q.empty()) { // 큐가 빌 때까지 반복 int cy = q.front().first; int cx = q.front().second; q.pop(); for (int dir = 0; dir < 4; ++dir) { // 상, 하, 좌, 우 방향 범위 int ny = cy + dy[dir]; // 새로운 y 위치 계산 int nx = cx + dx[dir]; // 새로운 x 위치 계산 if (ny < 0 || ny >= n || nx < 0 || nx >= n) continue; // 격자 밖에 있다면 다음 방향 확인 if (visit[ny][nx]) continue; // 이미 방문한 경우 다음 방향 확인 int diff = abs(a[ny][nx] - a[cy][cx]); // 인접한 나라의 인구 차이 계산 if (l <= diff && diff <= r) { // 인구 차이가 l 이상 r 이하일 경우 q.push(make_pair(ny, nx)); // 큐에 위치 저장 visit[ny][nx] = true; // 방문 표시 open.push_back(make_pair(ny, nx)); // 연합국 위치 저장 벡터에 추가 } } } return open.size() > 1; // 연합국이 2개 이상이면 true 반환, 아니면 false 반환 } int main() { ios_base::sync_with_stdio(false); cin.tie(nullptr); cin >> n >> l >> r; // 입력: n, l, r for (int i = 0; i < n; ++i) { for (int j = 0; j < n; ++j) { cin >> a[i][j]; // 입력: 각 나라의 인구 수 행렬 a } } int ans = 0; // 선언 및 초기화: 인구 이동이 발생한 총 라운드 수 while (true) { // 인구 이동이 더 이상 발생하지 않을 때까지 반복 memset(visit, false, sizeof(visit)); // 방문 배열 초기화 bool flag = false; // 선언 및 초기화: 이동 여부 플래그 for (int i = 0; i < n; ++i) { for (int j = 0; j < n; ++j) { if (bfs(i, j)) { // 해당 위치에서 bfs 실행 후 연합국이 2개 이상일 경우 flag = true; // 이동 여부 플래그 true로 설정 int sum = 0; // 선언 및 초기화: 연합국 인구 수 총합 for (auto& p : open) { sum += a[p.first][p.second]; // 연합국 인구 수 누적 } int avg = sum / open.size(); // 연합국 인구 평균 for (auto& p : open) { a[p.first][p.second] = avg; // 연합국별로 새로운 인구 수 할당 } } } } if (!flag) break; // 이동이 발생하지 않은 경우 라운드 종료 ans++; // 인구 이동이 발생한 경우 라운드 수 증가 } cout << ans << '\n'; // 결과 출력: 인구 이동이 발생한 총 라운드 수 return 0; }
'⭐ 코딩테스트 > 백준' 카테고리의 다른 글
[백준 1629번 C/C++] 곱셈 (0) | 2023.07.31 |
---|---|
[백준 13305번 C/C++] 주유소 (0) | 2023.07.28 |
[백준 11404번 C/C++] 플로이드 (0) | 2023.07.25 |
[백준 2293번 C/C++] 동전 1 (0) | 2023.07.24 |
[백준 2447번 C/C++] 별 찍기 (0) | 2023.07.21 |
댓글
이 글 공유하기
다른 글
-
[백준 1629번 C/C++] 곱셈
[백준 1629번 C/C++] 곱셈
2023.07.31 -
[백준 13305번 C/C++] 주유소
[백준 13305번 C/C++] 주유소
2023.07.28 -
[백준 11404번 C/C++] 플로이드
[백준 11404번 C/C++] 플로이드
2023.07.25 -
[백준 2293번 C/C++] 동전 1
[백준 2293번 C/C++] 동전 1
2023.07.24
댓글을 사용할 수 없습니다.