Link https://www.acmicpc.net/problem/1963
소스결과 1996 KB / 0 ms
출처 Baekjoon, NWERC 2006
언어 C++ 17
분류 BFS 소수
설명
소수를 좋아하는 창영이가 4자리 소수인 현재 비밀번호를 다른 4자리 소수인 비밀번호로 바꾸려고 할 때. 한번에 한 자리씩 바꾸어서 다른 비밀번호가 되는 최소의 경우의 수를 출력한다.
소수에 집착하는 창영이 그리고 비밀번호를 한 번에 한 자리 밖에 못바꾸는 괴상망측한 게임. 현실에서는 절대 보기 힘든 조합이다.
먼저 현재 값이 소수인지 판별 하기 위한 방법이 필요하다. 탐색의 경우가 여러 번 존재하기 때문에 소수를 판별해 줄 부분이 필요하다.
범위가 최대 9999 이기에 에라토스테네스의 체를 이용해 소수를 미리 구해두자.
한번에 한 자리를 바꿀 수 있기 때문에 1천의 자리 1백의 자리 1십의 자리 1의자리 4부분으로 나누어 총 39번을 확인한다.
하지만 39번 전체가 소수가 아니기에 많아봐야 3번정도로 줄어든다.
Queue에 들어가는 경우는 한 자리를 바꾼 수가 소수인지, 일전에 탐색 했던 숫자인지 판별해 만족하는 조건 일 때에만 Queue에 넣는다.
알고리즘
1. 에라토스테네스의 체를 이용해 0 ~ 9999 까지의 소수 배열을 미리 만들어 둔다.
2. 초기 값을 기준으로 각각의 자리를 변경 했을 때 소수 이면서 탐색 되지 않은 값을 Queue에 넣는다.
3. Queue에서 꺼낸 값이 목표 값과 일치하면 탐색을 종료한다.
4. 출력
소스코드
#include <iostream>
#include <cstring>
#include <queue>
using namespace std;
const int MAX = 10000;
const int RANGE_MAX = 9000;
bool prime[MAX + 1];
void init()
{
prime[0] = prime[1] = true;
for (int i = 2; i < (MAX / 2) + 1; i++)
{
if (prime[i])
continue;
for (int j = 2; (i * j) < MAX + 1; j++)
prime[i * j] = true;
}
}
int main()
{
int tcc = 0;
cin >> tcc;
init(); // prime Init
for (int i = 0; i < tcc; i++)
{
int start, des;
int count = 0;
queue<int> q;
queue<int> nextQ;
bool isOver = false;
bool check[RANGE_MAX];
memset(check, false, sizeof(check));
cin >> start >> des;
q.push(start);
check[start] = true;
while (!q.empty())
{
while (!q.empty())
{
int cur = q.front();
q.pop();
if (cur == des)
{
isOver = true;
break;
}
int posMax = 10000;
int posMin = 1000;
for (int i = 0; i < 4; i++)
{
for (int j = 0; j < 10; j++)
{
if (i == 0 && j == 0)
continue;
int cal = ((cur / posMax) * posMax) + (j * posMin) + (cur % posMin);
if (!prime[cal] && !check[cal-1000])
{
check[cal-1000] = true;
nextQ.push(cal);
}
}
posMax /= 10;
posMin /= 10;
}
}
if (isOver)
break;
else
{
while (!nextQ.empty())
{
q.push(nextQ.front());
nextQ.pop();
}
++count;
}
}
cout << count << '\n';
}
return 0;
}
'Algorithm > BFS' 카테고리의 다른 글
BaekJoon 6593 상범 빌딩 (0) | 2019.02.03 |
---|---|
BaekJoon 2573 빙산 (0) | 2019.02.03 |
BaekJoon 12761 돌다리 (0) | 2019.02.01 |
BaekJoon 4179 불! (0) | 2019.02.01 |
BaekJoon 5427 불 (0) | 2019.01.29 |