[SW Expert] [모의 SW 역량테스트] 5644번 무선 충전 (Java)
Algorithm/SW Expert Academy

[SW Expert] [모의 SW 역량테스트] 5644번 무선 충전 (Java)

728x90

SW Expert [모의 SW 역량테스트] 5644번 무선 충전 :

https://swexpertacademy.com/main/code/problem/problemDetail.do?contestProbId=AWXRDL1aeugDFAUo

 

 

이번 문제 풀이에는 Index와 BC 클래스를 만들어서 사용했다.

Index 클래스는 평소 자주 사용했던 클래스로 A, B의 위치를 나타낸다.

BC 클래스는 문제에서 주어진 BC의 정보를 담는 클래스로 BC의 위치와 범위(range), 성능(power)을 변수로 가지고 있다.

 

A와 B가 이동하는 정보를 배열로 저장한 뒤,

for문으로 탐색하며 각 시간마다의 boolean[2][a]의 check 배열을 계산한다. (getCheck 함수)

check 배열은 다음과 같은 형태를 띄고 있다.

 

위는 t = 11 일때의 check 배열이다.

1이 의미하는 바는 사용자가 BC의 범위 안에 포함되어 있는지 아닌지이다.

t = 11 일때 A는 BC 1과 BC 3에 포함되어 있고, B는 BC 1에만 포함되어 있다.

 

각 시간마다 check 배열을 얻었으면, 해당 시간에서 충전 양의 최댓값을 구할 수 있다.

(A, B)가 가질 수 있는 경우의 수는 (1, 1), (1, 2), (1, 3), (2, 1), (2, 2),... 해서 총 9가지 경우의 수가 나온다.

A와 B가 0인 경우를 제외하여 계산하면 시간은 좀 더 빠르겠지만, BC의 최대 개수가 8개이고, 최대 경우의 수가 64이므로

그냥 모든 경우의 수에 대해서 계산을 해주었다.

이 때, A와 B가 동시에 같은 BC에 있다면 해당 BC의 충전 양을 절반씩만 가지므로 이를 체크해준다.

 

결과적으로 getMax 함수는 특정 시간에서의 A와 B가 가질 수 있는 충전 양 합의 최댓값을 반환해준다.

이를 모든 시간에 대해서 합산을 해주면 결괏값이 나오게 된다.

 

 

코드

import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.util.StringTokenizer;

public class Main {
    private static int m, a;
    private static int[] moveA, moveB;
    private static BC[] bcList;
    private static Index A, B;
    private static int[] dx = {0, -1, 0, 1, 0};
    private static int[] dy = {0, 0, 1, 0, -1};

    public static void main(String[] args) throws Exception {
        BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
        StringTokenizer st;

        int T = Integer.parseInt(br.readLine());

        for (int t = 1; t <= T; t++) {
            st = new StringTokenizer(br.readLine());

            m = Integer.parseInt(st.nextToken());
            a = Integer.parseInt(st.nextToken());

            bcList = new BC[a];
            moveA = new int[m + 1];
            moveB = new int[m + 1];
            moveA[0] = 0;
            moveB[0] = 0;
            A = new Index(0, 0);
            B = new Index(9, 9);

            st = new StringTokenizer(br.readLine());
            for (int i = 1; i <= m; i++) moveA[i] = Integer.parseInt(st.nextToken());

            st = new StringTokenizer(br.readLine());
            for (int i = 1; i <= m; i++) moveB[i] = Integer.parseInt(st.nextToken());

            for (int i = 0; i < a; i++) {
                st = new StringTokenizer(br.readLine());

                int x = Integer.parseInt(st.nextToken());
                int y = Integer.parseInt(st.nextToken());
                int C = Integer.parseInt(st.nextToken());
                int P = Integer.parseInt(st.nextToken());

                bcList[i] = new BC(y - 1, x - 1, C, P);
            }

            int answer = solution();
            System.out.println("#" + t + " " + answer);
        }
    }

    private static int solution() {
        int sum = 0;
        for (int t = 0; t <= m; t++) {
            A.setIndex(moveA[t]); // A, B 이동
            B.setIndex(moveB[t]);
            sum += getMax(getCheck(A, B));
        }
        return sum;
    }

    private static int getMax(boolean[][] check) { // 해당 위치에서의 최대 양 반환
        int max = 0, value;
        boolean checkA, checkB;
        for (int i = 0; i < a; i++) {
            checkA = check[0][i];
            for (int j = 0; j < a; j++) {
                checkB = check[1][j];
                value = 0;

                // 같은 범위에 있는 경우
                if (i == j && checkA && checkB) value = bcList[i].power;
                else {
                    if (checkA) value += bcList[i].power;
                    if (checkB) value += bcList[j].power;
                }
                max = Math.max(max, value);
            }
        }
        return max;
    }

    private static boolean[][] getCheck(Index idxA, Index idxB) {
        boolean[][] result = new boolean[2][a];

        for (int i = 0; i < a; i++) {
            BC bc = bcList[i];
            if (getDistance(idxA, bc.index) <= bc.range) result[0][i] = true;
            if (getDistance(idxB, bc.index) <= bc.range) result[1][i] = true;
        }
        return result;
    }

    private static int getDistance(Index a, Index b) {
        return Math.abs(a.x - b.x) + Math.abs(a.y - b.y);
    }

    static class Index {
        int x, y;

        public Index(int x, int y) {
            this.x = x;
            this.y = y;
        }

        public void setIndex(int dir) {
            this.x = x + dx[dir];
            this.y = y + dy[dir];
        }
    }

    static class BC {
        Index index;
        int range, power;

        public BC(int x, int y, int range, int power) {
            this.index = new Index(x, y);
            this.range = range;
            this.power = power;
        }
    }
}
728x90