문제
https://softeer.ai/practice/6246
풀이(19분)
import java.io.*;
import java.util.*;
public class Main {
// dfs로 하면서 추적하자.
// m의 포인트를 리스트로 관리하고, 지도상에는 2로 표시하자.
// 만약 dfs 이동 중에 2를 만난다면 현재 포인트 인덱스와 일치하는지를 판단하자.
// 아니라면 리턴을 해주어야 한다!
static int n, m, answer;
static int[][] map;
static boolean[][] visited;
static Point[] order;
static int[] dx = {0, 0, -1, 1};
static int[] dy = {-1, 1, 0, 0};
public static void main(String[] args) throws IOException{
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
StringTokenizer st;
st = new StringTokenizer(br.readLine());
n = Integer.parseInt(st.nextToken());
m = Integer.parseInt(st.nextToken());
map = new int[n][n];
visited = new boolean[n][n];
order = new Point[m];
for(int i = 0; i < n; i++){
st = new StringTokenizer(br.readLine());
for(int j = 0; j < n; j++){
map[i][j] = Integer.parseInt(st.nextToken());
}
}
for(int i = 0; i < m; i++){
st = new StringTokenizer(br.readLine());
int row = Integer.parseInt(st.nextToken()) - 1;
int col = Integer.parseInt(st.nextToken()) - 1;
map[row][col] = 2;
order[i] = new Point(row, col);
}
dfs(order[0], 0);
System.out.println(answer);
}
static void dfs(Point p, int depth){
int nowRow = p.row;
int nowCol = p.col;
visited[nowRow][nowCol] = true;
// 이 칸이 2이고, 현재 순서대로 가야 하는 포인트라면
if(map[nowRow][nowCol] == 2){
if(depth >= m || nowRow != order[depth].row || nowCol != order[depth].col){
visited[nowRow][nowCol] = false; // 빠르게 백트래킹
return;
}
depth++; // 올바른 순서의 포인트일 경우에만 증가
}
// 모든 포인트를 순서대로 방문했으면 성공!
if(depth == m){
answer++;
visited[nowRow][nowCol] = false;
return;
}
for(int i = 0; i < 4; i++){
int nextRow = nowRow + dx[i];
int nextCol = nowCol + dy[i];
if(isBounds(nextRow, nextCol)){
if(!visited[nextRow][nextCol] && map[nextRow][nextCol] != 1){
dfs(new Point(nextRow, nextCol), depth);
}
}
}
visited[nowRow][nowCol] = false; // 백트래킹
}
static boolean isBounds(int row, int col){ // 격자 범위 안에 있는지 확인
return row >= 0 && row < n && col >= 0 && col < n;
}
static class Point{
int row, col;
public Point(int row, int col) {
this.row = row;
this.col = col;
}
}
}
문제 풀이 전략
dfs를 통해 경로를 계산한다. map에는 2라는 값을 방문해야하는 지점으로 체크한다.
[도구정리] DFS, BFS
DFS(깊이 우선 탐색) and BFS(너비 우선 탐색) 두 가지 모두 조건에 부합하는 정답을 찾기 위해 탐색을 실행하는 알고리즘이다. BFS는 너비 우선 탐색을 진행한다. 위의 그림을 보면 루트 노드에서 시
to-travel-coding.tistory.com
경로를 따라갈 때, 방문해야 하는 지점을 depth로 정해두고 이를 만족하는지 확인한다.
확인하는 과정에서 순서에 어긋난다면 백트래킹과 return을 즉각적으로 해준다.
최종적으로 도착해야하는 포인트에 도착했다면 정답을 +1 해준다.
'문제 풀이 > 소프티어' 카테고리의 다른 글
[소프티어] [HSAT 7회 정기 코딩 인증평가 기출] 자동차 테스트(JAVA) (0) | 2025.04.17 |
---|---|
[소프티어] [HSAT 1회 정기 코딩 인증평가 기출] 로봇이 지나간 경로 (0) | 2025.03.31 |
[소프티어] [HSAT 2회 정기 코딩 인증평가 기출] 사물인식 최소 면적 산출 프로그램(JAVA) (0) | 2025.03.30 |
[소프티어] 스마트 물류(JAVA) (0) | 2025.03.30 |
[소프티어] 동계 테스트 시점 예측(JAVA) (0) | 2025.03.29 |