작성
·
271
·
수정됨
0
안녕하세요 선생님. 코딩테스트 강의 잘 듣고 있습니다.
15684번 문제 코드를 짰는데, 답 코드랑 비교해서 로직은 맞는 것 같은데 자꾸 시간초과가 납니다.
이유를 잘 모르겠어서 질문 드립니다.
#include <iostream>
#include <algorithm>
#include <vector>
using namespace std;
int H, W, P;
bool isGaro[12][12][32]; //[시작점][끝점][가로선을 놓을 수 있는 위치]
int ans = 4; //최대값 3보다 높은 값으로 초기화
bool check()
{
for (int i = 1; i <= H; i++) {
int now = i;
for (int j = 1; j <= P; j++) {
//자신 기준으로 오른쪽에 선이 있음
if (isGaro[now][now + 1][j]) {
now++; //오른쪽으로 이동
continue;
}
//자신 기준으로 왼쪽에 선이 있음
if (isGaro[now - 1][now][j]) {
now--; //왼쪽으로 이동
continue;
}
}
if (now != i) {
//한번이라도 번호가 다르면 실패
return false;
}
}
return true;
}
void go(int pos ,int garoCnt)
{
//만약 현재 갱신된 가로선 개수보다 개수가 많으면 바로 종료
if (ans <= garoCnt || garoCnt > 3 ) return;
//현재 모든 세로선이 사다리 게임을 진행했을 때
//같은 번호가 나오는 지 체크
//만약 모두 같은 번호가 나오면
//갯수 갱신한 뒤에 종료
if (check()) {
ans = min(ans, garoCnt);
return;
}
//세로선 번호
int s = pos / 1000;
//가로선 번호
int p = pos % 1000;
//만약 s == H이면
//다음 가로선으로 넘어가기
//cout << "세로선 번호 : " << s << ' ' << "가로선 번호 : " << p << '\n';
for (int i = p; i <= P; i++) {
for (int j = 1; j <= H; j++) {
//현재 위치에 있는 가로선을 추가함
if (!isGaro[j][j + 1][i] && !isGaro[j-1][j][i] && !isGaro[j][j][i]) {
isGaro[j][j + 1][i] = true;
go(1000 * (j + 1) + p, garoCnt + 1);
isGaro[j][j + 1][i] = false;
}
}
}
}
int main(int argc, char** argv) {
cin >> H >> W >> P;
for (int i = 0; i < W; i++) {
int a, b;
cin >> a >> b;
isGaro[b][b + 1][a] = true; //b번 세로선과 b+1번 세로선을 a번 점선위치에서 연결
}
//만약 놓여져 있는 가로선이 없다면
//0을 출력
if (W == 0) {
cout << 0;
return 0;
}
//1000 / 1000 = s
//1000 % 1000 = p
//1000 * s + p
//세로선과 가로선 모두 1,1에서 시작
go(1000* 1 + 1,0);
if (ans >= 4) {
cout << -1;
}
else cout << ans;
}
답변 1
0
안녕하세요 윤신님 ㅎㅎ
제일 중요한 핵심 로직은 다음과 같고...
1.함수 내에서는 특정 위치에 가로선을 추가하고 (isGaro[j][j + 1][i] = true;)
2.그 결과를 검사한 후 (check 함수)
3.다음 재귀 호출을 통해 다른 위치에 가로선을 추가합니다.
4. 그리고 나서 가로선을 제거하고 (isGaro[j][j + 1][i] = false;) 다른 가능한 위치를 탐색합니다.
3차원 배열 말고는 로직도 괜찮은 거 같아요...
몇번 고쳐해서 시도해봤는데 다 안되네요 저도 ㅠㅠ
도움이 되지 못해 죄송합니다 ㅠㅠ
일단 제가 수정한 마지막 코드는 다음과 같아요 이렇게 하면 좀 더 효율적입니다. 탐색한 지점 탐색x + 가장자리부분 어차피 사다리 못붙일거 고려해서 윤신님 코드 수정한 코드입니다.
for (int i = p; i <= P; i++) {
for (int j = (i == p) ? s : 1; j < H; j++) {
//현재 위치에 있는 가로선을 추가함
if (!isGaro[j][j + 1][i] && !isGaro[j-1][j][i] && !isGaro[j][j][i]) {
isGaro[j][j + 1][i] = true;
20점짜리 답변.. 드려서 죄송합니다.
저도 많이 해봤는데 효율적으로 잘 안만들어지네요 ㅠㅠ
죄송합니다.