[๋ฐฑ์ค] [C++] ๐ฎ ๊ตฌ์ฌ ํ์ถ 2 13460๋ฒ
๐ก ๋ฌธ์ ์ค๋ช

bfs ์ต๋จ๊ฑฐ๋ฆฌ ๋ฌธ์ ์ด๋ฉด์, ๊ณต์ด ๋๊ฐ๋ผ์ ๊ตฌํ์ด ๊น๋ค๋กญ๋ค.
๐ก ์ด๋ ํจ์
4 ๋ฐฉํฅ์ผ๋ก ์ด๋ํ์๋,
๋นจ๊ฐ๊ณต๊ณผ ํ๋ ๊ณต์ ์์น๋ฅผ returnํด์ฃผ๋ ํจ์๋ฅผ ๋ง๋ค์๋ค.
ํญ์ ๋ฐ๊นฅ์ชฝ์๋ ๋ฒฝ์ด ์๊ธฐ ๋๋ฌธ์ ๋ฐ์ผ๋ก ๋จ์ด์ง ์ผ์ ์์ผ๋ ๋ฒฝ๊ณผ ๋ง๋ ๋๊น์ง ์ด๋์์ผ์ค๋ค.
- ์ค๊ฐ์ ๊ณต์ด ๊ตฌ๋ฉ์ผ๋ก ๋ค์ด๊ฐ๋ฉด ํน๋ณํ๊ฒ ์ฒ๋ฆฌํด์ฃผ๊ธฐ ์ํด์, ์ขํ๋ฅผ ์์๋ก ํ๊ธฐํด์ค๋ค.
๋ง์ฝ ํ๋ ๊ณต๊ณผ ๋นจ๊ฐ ๊ณต์ ์์น๊น์ง ์๊ฐํด์ ๊ตฌํํ๋ ค๋ฉด ์์ฃผ ๋ณต์กํ๊ณ ๊ธธ์ด์ง๋๋ฐ,
๊ทธ๋ ๊ฒ ํ์ง ๋ง๊ณ ๋ฌด์ํ๊ณ ์ด๋ ํ ํ, ๋ ๊ณต์ ์ขํ๊ฐ ๊ฐ๋ค๋ฉด ์ฒ๋ฆฌ๋ฅผ ํด์ฃผ๋ฉด ๋๋ค.
- ์ฒ๋ฆฌ ๋ฐฉ๋ฒ
- ์๋ ์ํ์์ ์ค๋ฅธ์ชฝ์ผ๋ก ๊ฐ๋ค๊ณ ํด๋ณด์.
- R . . . B . . #
- ๊ทธ๋ฅ ์ด๋์ ํ๋ฉด R๊ณผ B๊ฐ ๊ฐ์ ์์น์ ์ฐํ ๊ฒ์ด๋ค.
- . . . . . . (RB) #
- ๊ฐ์ ์์น๋ผ๋ฉด, ๋ฐฉํฅ์ ๋ฐ๋ผ์ ๋ค๋ฐ๋ผ์ค๋ ์ ๋ฅผ ํ์นธ ์ ์ผ๋ก ๋๋ฆฌ๋ฉด ๋๋ค.
- . . . . . R B #
// ์๋, ์, ์ค๋ฅธ, ์ผ
const int dx[] = { 1,-1,0,0 };
const int dy[] = { 0,0,1,-1 };
tuple<int,int,int,int> go(int dir, int rx, int ry, int bx, int by){
int nrx=rx, nry=ry, nbx=bx, nby=by;
// Red
while(true){
nrx+=dx[dir]; nry+=dy[dir];
if (board[nrx][nry]=='#') {
nrx-=dx[dir]; nry-=dy[dir];
break;
}
// ๊ตฌ๋ฉ์ผ๋ก ๋น ์ง : -1๋ก ํ์
if (board[nrx][nry]=='O'){
nrx = -1; nry = -1;
break;
}
}
// Blue
while(true){
nbx+=dx[dir]; nby+=dy[dir];
if (board[nbx][nby]=='#') {
nbx-=dx[dir]; nby-=dy[dir];
break;
}
// ๊ตฌ๋ฉ์ผ๋ก ๋น ์ง : -2๋ก ํ์
if (board[nbx][nby]=='O'){
nbx = -2; nby = -2;
break;
}
}
// ๋ ์ขํ๊ฐ ๊ฐ๋ค๋ฉด ๊ฒน์น ์ ์์ผ๋ฏ๋ก ์ฒ๋ฆฌ
if(nrx==nbx && nry==nby){
// ์๋๋ก ๋ด๋ ค๊ฐ๊ฑฐ๋ผ๋ฉด ์์์๋๊ฑธ ํ๋จ๊ณ ์ ์ผ๋ก
if (dir==0){
if (bx<rx) nbx -= dx[dir];
else nrx -= dx[dir];
}
// ์๋ก ์ฌ๋ผ๊ฐ๊ฑฐ๋ผ๋ฉด ์๋์๋๊ฑธ ํ๋จ๊ณ ์ ์ผ๋ก
else if (dir==1){
if (bx>rx) nbx -= dx[dir];
else nrx -= dx[dir];
}
// ์ค๋ฅธ์ชฝ์ผ๋ก ๊ฐ๊ฑฐ๋ผ๋ฉด ์ผ์ชฝ์ ์๋๊ฑธ ํ๋จ๊ณ ์ ์ผ๋ก
else if (dir==2){
if (by<ry) nby -= dy[dir];
else nry -= dy[dir];
}
// ์ผ์ชฝ์ผ๋ก ๊ฐ๊ฑฐ๋ผ๋ฉด ์ค๋ฅธ์ชฝ์ ์๋๊ฑธ ํ๋จ๊ณ ์ ์ผ๋ก
else if (dir==3){
if (by>ry) nby -= dy[dir];
else nry -= dy[dir];
}
}
return {nrx, nry, nbx, nby};
}
๐ก BFS ์ต๋จ๊ฑฐ๋ฆฌ
BFS ์ด๊ธฐ ๋๋ฌธ์ dist๊ฐ ๋ฎ์ ๊ฒ๋ถํฐ ์ฒ๋ฆฌ๋๋ค.
10๋ฒ ์์ ๋์ฐฉํ์ง ๋ชปํ๋ ๊ฒฝ์ฐ ๋ฐ๋ก ์ข ๋ฃ์์ผ์ฃผ๋ฉด ๋๋ค.
์ go ํจ์๋ฅผ ํตํด B์ x์ขํ๊ฐ -2๊ฐ ๋์๋ค๋ฉด ๋น ์ง ๊ฒ์ด๋ฏ๋ก, ๋์ด์ ์งํํ์ง ์๊ณ ๋ค์ ํ๋ก ์ด๋ํ๋ค.
B๋ ์๋น ์ง๋ฉด์ R์ x์ขํ๊ฐ -1์ด๋ฉด ์ฑ๊ณตํ๊ฒ์ด๋ฏ๋ก dist+1 ์ ๋ฆฌํดํ๋ค.
int bfs(int start_rx, int start_ry, int start_bx, int start_by){
// Red ์ขํ, Blue์ขํ, ๊ฑฐ๋ฆฌ
queue<tuple<int,int,int,int,int>> q;
q.push({start_rx, start_ry, start_bx, start_by, 0});
visited[start_rx][start_ry][start_bx][start_by]=true;
while (!q.empty()){
auto [rx, ry, bx, by, now_dist] = q.front();
// 10๋ฒ ์์ ๋์ฐฉ ๋ชปํ์ ๊ฒฝ์ฐ
// 10๋ ํฌํจํด์ผํ๋ ์ด์ : ์ง๊ธ๊น์ง ์จ๊ฒ 10์ด๋ฉด,
// ๋ค์๋จ๊ณ์ ๋๋ฌํด๋ return์ 11์ด ๋๊ธฐ ๋๋ฌธ์
if (now_dist>=10) {
return -1;
}
q.pop();
for (int i=0; i<4; i++){
// ์ด๋
auto [nrx, nry, nbx, nby] = go(i, rx, ry, bx, by);
// ํ๋์์ด ๊ตฌ๋ฉ์ ๋น ์ง
if (nbx==-2) continue;
// ํ๋์์ ์๋น ์ง๊ณ ๋นจ๊ฐ์์ด ๊ตฌ๋ฉ์ ๋น ์ง๋ฉด ์ข
๋ฃ
if (nrx==-1) return now_dist+1;
if (visited[nrx][nry][nbx][nby]) continue;
visited[nrx][nry][nbx][nby] = true;
q.push({nrx, nry, nbx, nby, now_dist + 1});
}
}
return -1; // ๋๋ฌ ๋ชปํ์ ๊ฒฝ์ฐ
}
๐ก ๋ด ํ์ด
#include <bits/stdc++.h>
#define FOR(i,a,b) for(int i=(a);i<(b);i++)
#define all(v) v.begin(), v.end()
using namespace std;
typedef long long ll;
typedef pair<int,int> pii; typedef pair<ll,ll> pll;
typedef tuple<int,int,int> tiii;
const int INF = 0x7f7f7f7f;
/*--
https://www.acmicpc.net/problem/13460
์ํ์ข์ฐ๋ก ๊ธฐ์ธ์ฌ์
R์ด O๋ก ๋ค์ด๊ฐ์ผํจ.
๋์์ R, B ๊ฐ ๋ค์ด๊ฐ๋ฉด ์๋จ
#์ ์ฅ์ ๋ฌผ, .์ ๋น๊ณต๊ฐ
*/
#define MAX 10
int N, M;
char board[MAX][MAX];
bool visited[MAX][MAX][MAX][MAX]; // ๋นจ๊ฐ ๊ตฌ์ฌ, ํ๋๊ตฌ์ฌ
// ์๋, ์, ์ค๋ฅธ, ์ผ
const int dx[] = { 1,-1,0,0 };
const int dy[] = { 0,0,1,-1 };
tuple<int,int,int,int> go(int dir, int rx, int ry, int bx, int by){
int nrx=rx, nry=ry, nbx=bx, nby=by;
// Red
while(true){
nrx+=dx[dir]; nry+=dy[dir];
if (board[nrx][nry]=='#') {
nrx-=dx[dir]; nry-=dy[dir];
break;
}
// ๊ตฌ๋ฉ์ผ๋ก ๋น ์ง : -1๋ก ํ์
if (board[nrx][nry]=='O'){
nrx = -1; nry = -1;
break;
}
}
// Blue
while(true){
nbx+=dx[dir]; nby+=dy[dir];
if (board[nbx][nby]=='#') {
nbx-=dx[dir]; nby-=dy[dir];
break;
}
// ๊ตฌ๋ฉ์ผ๋ก ๋น ์ง : -2๋ก ํ์
if (board[nbx][nby]=='O'){
nbx = -2; nby = -2;
break;
}
}
// ๋ ์ขํ๊ฐ ๊ฐ๋ค๋ฉด ๊ฒน์น ์ ์์ผ๋ฏ๋ก ์ฒ๋ฆฌ
if(nrx==nbx && nry==nby){
// ์๋๋ก ๋ด๋ ค๊ฐ๊ฑฐ๋ผ๋ฉด ์์์๋๊ฑธ ํ๋จ๊ณ ์ ์ผ๋ก
if (dir==0){
if (bx<rx) nbx -= dx[dir];
else nrx -= dx[dir];
}
// ์๋ก ์ฌ๋ผ๊ฐ๊ฑฐ๋ผ๋ฉด ์๋์๋๊ฑธ ํ๋จ๊ณ ์ ์ผ๋ก
else if (dir==1){
if (bx>rx) nbx -= dx[dir];
else nrx -= dx[dir];
}
// ์ค๋ฅธ์ชฝ์ผ๋ก ๊ฐ๊ฑฐ๋ผ๋ฉด ์ผ์ชฝ์ ์๋๊ฑธ ํ๋จ๊ณ ์ ์ผ๋ก
else if (dir==2){
if (by<ry) nby -= dy[dir];
else nry -= dy[dir];
}
// ์ผ์ชฝ์ผ๋ก ๊ฐ๊ฑฐ๋ผ๋ฉด ์ค๋ฅธ์ชฝ์ ์๋๊ฑธ ํ๋จ๊ณ ์ ์ผ๋ก
else if (dir==3){
if (by>ry) nby -= dy[dir];
else nry -= dy[dir];
}
}
return {nrx, nry, nbx, nby};
}
int bfs(int start_rx, int start_ry, int start_bx, int start_by){
// Red ์ขํ, Blue์ขํ, ๊ฑฐ๋ฆฌ
queue<tuple<int,int,int,int,int>> q;
q.push({start_rx, start_ry, start_bx, start_by, 0});
visited[start_rx][start_ry][start_bx][start_by]=true;
while (!q.empty()){
auto [rx, ry, bx, by, now_dist] = q.front();
// 10๋ฒ ์์ ๋์ฐฉ ๋ชปํ์ ๊ฒฝ์ฐ
// 10๋ ํฌํจํด์ผํ๋ ์ด์ : ์ง๊ธ๊น์ง ์จ๊ฒ 10์ด๋ฉด,
// ๋ค์๋จ๊ณ์ ๋๋ฌํด๋ return์ 11์ด ๋๊ธฐ ๋๋ฌธ์
if (now_dist>=10) {
return -1;
}
q.pop();
for (int i=0; i<4; i++){
// ์ด๋
auto [nrx, nry, nbx, nby] = go(i, rx, ry, bx, by);
// ํ๋์์ด ๊ตฌ๋ฉ์ ๋น ์ง
if (nbx==-2) continue;
// ํ๋์์ ์๋น ์ง๊ณ ๋นจ๊ฐ์์ด ๊ตฌ๋ฉ์ ๋น ์ง๋ฉด ์ข
๋ฃ
if (nrx==-1) return now_dist+1;
if (visited[nrx][nry][nbx][nby]) continue;
visited[nrx][nry][nbx][nby] = true;
q.push({nrx, nry, nbx, nby, now_dist + 1});
}
}
return -1; // ๋๋ฌ ๋ชปํ์ ๊ฒฝ์ฐ
}
int main(){
ios_base::sync_with_stdio(0); cin.tie(0);
cin >> N >> M;
for (int i=0; i<N; i++){
for (int j=0; j<M; j++){
cin >> board[i][j];
}
}
// ์์ ์ง์ ์ฐพ๊ธฐ
int rx, ry, bx, by;
for (int i=0; i<N; i++)
for (int j=0; j<M; j++)
if (board[i][j]=='R'){
rx = i; ry = j; break;
}
for (int i=0; i<N; i++)
for (int j=0; j<M; j++)
if (board[i][j]=='B'){
bx = i; by = j; break;
}
cout << bfs(rx, ry, bx, by);
return 0;
}
๐ก ๋ง๋ฌด๋ฆฌ
๋ด๊ฐ ํ๊ณ ๋ ๋นจ๊ฐ ๊ณต๊ณผ ํ๋ ๊ณต์ด ๋ง๋ ๋ ์ฒ๋ฆฌ๋ฅผ ์ ํด์ค ๊ฒ ๊ฐ์์ ๋ง์กฑํ๋ค.
์ด ์ฝ๋๋ฅผ ์กฐ๊ธ๋ง ์์ ํด๋ ๊ตฌ์ฌ ํ์ถ 3, ๊ตฌ์ฌ ํ์ถ 4๋ ์์ฝ๊ฒ ํ ์ ์๋ค.