백준 23288 주사위 굴리기2 (JAVA)

2024. 4. 7. 00:15·BackEnd/알고리즘 공부

문제 설명

https://www.acmicpc.net/problem/23288

 

23288번: 주사위 굴리기 2

크기가 N×M인 지도가 존재한다. 지도의 오른쪽은 동쪽, 위쪽은 북쪽이다. 지도의 좌표는 (r, c)로 나타내며, r는 북쪽으로부터 떨어진 칸의 개수, c는 서쪽으로부터 떨어진 칸의 개수이다. 가장 왼

www.acmicpc.net

  • 처음 주사위는 지도 위에 윗면이 1, 아래는 6
  • 처음 이동 방향은 동쪽
  • 조건

  • 점수 계산

 

문제에 대한 아이디어

이 문제를 해결하기 위해서는 필요한 메소드를 생각해야 할 필요가 있습니다. 

  • 주사위 움직이는 메소드
  • 위치를 움직이는 메소드
  • 방향을 정하는 메소드
  • 점수를 계산하는 메소드

주사위를 움직이는 메소드

    public static void moveDice(int dir) {
        if(dir == 1) { // 동쪽
            int temp = dice[6];
            dice[6] = dice[3];
            dice[3] = dice[1];
            dice[1] = dice[4];
            dice[4] = temp;
        }
        else if (dir == 2) { // 남쪽
            int temp = dice[6];
            dice[6] = dice[5];
            dice[5] = dice[1];
            dice[1] = dice[2];
            dice[2] = temp;

        }
        else if (dir == 3) { //서쪽
            int temp = dice[6];
            dice[6] = dice[4];
            dice[4] = dice[1];
            dice[1] = dice[3];
            dice[3] = temp;
        }
        else {
            int temp = dice[6];
            dice[6] = dice[2];
            dice[2] = dice[1];
            dice[1] = dice[5];
            dice[5] = temp;
        }
    }

코드를 더 예쁘게 짤 수도 있을 것 같지만 보자마자 생각난 방법은 위의 코드였습니다. 동, 서, 남, 북으로 움직일 때 위의 전개도의 숫자 중 바뀌는 것을 찾아 순서대로 바꾸어 주었습니다.

좌표 변경

public static void move(Pair now, int n , int m) {
        if(nowDir == 1) {
            if(now.x + 1 <= m){
                now.x += 1;
                moveDice(1);
            }
            else {
                now.x -= 1;
                moveDice(3);
                nowDir = 3;
            }
        }
        else if (nowDir == 2) {
            if(now.y + 1 <= n){
                now.y += 1;
                moveDice(2);
            }
            else {
                now.y -= 1;
                moveDice(4);
                nowDir = 4;
            }

        }
        else if (nowDir == 3) {
            if(0 < now.x - 1 ){
                now.x -= 1;
                moveDice(3);
            }
            else {
                now.x += 1;
                moveDice(1);
                nowDir = 1;
            }
        }
        else {
            if(0 < now.y - 1) {
                now.y -= 1;
                moveDice(4);
            }
            else {
                now.y += 1;
                moveDice(2);
                nowDir = 2;
            }
        }
    }

좌표 변경 동안 현재의 방향에서 움직일 때 범위를 벗어나지 않으면 그 방향으로 움직이도록 설정했습니다. 또한 벽을 만나면 반대 방향으로 변경했습니다. 방향을 변경하고 나서는 moveDice를 통해 주사위 또한 변경해 주었습니다. 지금 생각해 보니 숫자를 쓰지 않고 nowDir만 적어도 될 것 같습니다.

방향 설정

public static void checkNext(int board[][], Pair now) {
        result += scores[now.y][now.x];
        if(board[now.y][now.x] < dice[6]) {
            nowDir = (nowDir + 1) % 5;
            if(nowDir == 0) nowDir = 1;
        }
        else if(board[now.y][now.x] > dice[6]) {
            nowDir = (nowDir - 1) % 5;
            if(nowDir == 0) nowDir = 4;
        }
    }

점수를 계산하고 다음 방향을 지정해 주었습니다. 조건에 따라 시계방향 90도와 반시계방향 90도를 생각해서 짜주었습니다.

점수 계산

input값을 확인하니 매시간 bfs를 돌아도 되지만 한 번 다 구해 놓고 사용하면 k가 커질 때는 유용하다고 생각했습니다.

 public static void score(int board[][], Pair now, int n , int m) {
        Deque<Pair> dq = new ArrayDeque<>();
        dq.add(now);
        visited[now.y][now.x] = true;
        int num = board[now.y][now.x];
        int size = 0;
        ArrayList<Pair> arr = new ArrayList<>();
        arr.add(now);
        while(!dq.isEmpty()){
            Pair temp = dq.removeFirst();
            size += 1;
            for(int i = 0; i < 4; ++i) {
                int ny = temp.y + dy[i];
                int nx = temp.x + dx[i];
                if(ny < 1 || ny > n || nx < 1 || nx > m) continue;
                if(visited[ny][nx]) continue;
                visited[ny][nx] = true;
                if(board[ny][nx] == num) {
                    dq.addLast(new Pair(ny,nx));
                    arr.add(new Pair(ny,nx));
                }
            }
        }
        for(int i = 0; i < arr.size(); ++i) {
            scores[arr.get(i).y][arr.get(i).x] = num*size;
        }
    }

제일 처음 반복문을 통해 scores 2차원 배열에 점수를 모두 적어주었습니다. 그 후 그 지점에 점수를 결과값에 더해주었습니다. 이렇게 하면 제일 처음 BFS할 때 빼고은 O(1)시간안에 점수를 더할 수 있습니다. 

 

전체 코드

https://github.com/SeWooooong/CodingTest_Practice/blob/main/%EB%B0%B1%EC%A4%80/Gold/23288.%E2%80%85%EC%A3%BC%EC%82%AC%EC%9C%84%E2%80%85%EA%B5%B4%EB%A6%AC%EA%B8%B0%E2%80%852/%EC%A3%BC%EC%82%AC%EC%9C%84%E2%80%85%EA%B5%B4%EB%A6%AC%EA%B8%B0%E2%80%852.java

 

CodingTest_Practice/백준/Gold/23288. 주사위 굴리기 2/주사위 굴리기 2.java at main · SeWooooong/CodingTe

자바로 연습하는 코딩테스트. Contribute to SeWooooong/CodingTest_Practice development by creating an account on GitHub.

github.com

 

'BackEnd > 알고리즘 공부' 카테고리의 다른 글

백준 17232 생명 게임 (JAVA)  (1) 2024.02.12
자바에서 정렬에 대해  (1) 2024.01.04
백준 16637 괄호 추가하기 (JAVA)  (0) 2023.10.27
등대 (프로그래머스) JAVA  (1) 2023.10.19
백준 17298 오큰수 자바  (2) 2023.10.18
'BackEnd/알고리즘 공부' 카테고리의 다른 글
  • 백준 17232 생명 게임 (JAVA)
  • 자바에서 정렬에 대해
  • 백준 16637 괄호 추가하기 (JAVA)
  • 등대 (프로그래머스) JAVA
인프라 감자
인프라 감자
  • 인프라 감자
    삶은 인프라
    인프라 감자
  • 전체
    오늘
    어제
    • 분류 전체보기 (243)
      • 클라우드&인프라 (28)
        • 인프라 공부 (4)
        • AWS 구조와 서비스 (18)
        • 클라우드 공부 (4)
        • Terraform (2)
      • AWS Cloud School (13)
        • project (5)
        • Linux, Network (6)
        • Docker (2)
      • BackEnd (162)
        • JAVA 공부 (15)
        • 알고리즘 공부 (71)
        • MySQL 문제 풀기 (8)
        • 스프링 핵심 원리 - 기본편 (18)
        • 스프링 MVC 1편 (4)
        • 자바 ORM 표준 JPA 프로그래밍 (21)
        • 실전! 스프링 부트와 JPA 활용1 (8)
        • 실전! 스프링 부트와 JPA 활용2 (5)
        • 스프링 데이터 JPA (8)
        • Querydsl (4)
      • 혼자하는 프로젝트 (32)
        • 배달의 민족 클론코딩 (7)
        • 나만의 프로젝트 (10)
        • 스프링 부트로 구현한 웹 (15)
  • 블로그 메뉴

    • 홈
    • 태그
    • 방명록
  • 링크

    • Email
    • GitHub
  • 공지사항

  • 인기 글

  • 태그

    linux
    정렬
    조합
    스프링 핵심 원리-기본편
    querydsl
    이것이 자바다
    완전탐색
    자바
    VPN
    자동 배포
    백트래킹
    상속
    네트워크 기본 용어
    디팬스 게임
    중첩 선언
    쿼드 압축
    유니온 파인드
    다이나믹 프로그래밍
    dp
    프로그래머스
  • 최근 댓글

  • 최근 글

  • hELLO· Designed By정상우.v4.10.3
인프라 감자
백준 23288 주사위 굴리기2 (JAVA)
상단으로

티스토리툴바