본문 바로가기
Algorithm/백준

[백준 / Java] 2477. 참외밭

by clean01 2024. 5. 28.

문제

 

풀이

1. 클래스, 변수 선언 및 입력 받기

Line이라는 클래스를 선언해줍니다.
Line 클래스에는 선의 길이와 방향이 들어갑니다.

  static ArrayList<Line> lines;
  static class Line {
    int len;
    int direction;

    Line(int direction, int len) {
      this.len = len;
      this.direction = direction;
    }
  }
    K = Integer.parseInt(br.readLine());

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

      int d = Integer.parseInt(st.nextToken()); // d는 방향을 의미합니다.
      int l = Integer.parseInt(st.nextToken()); // l은 변의 길이를 의미합니다.

      lines.add(new Line(d, l));
    }

 

2. 가로, 세로에서 가장 긴 변 구하기

입력으로 들어오는 도형은 항상 ㄱ 을 회전시킨 모양이므로, 큰 직사각형에서 작은 직사각형이 빠진 모양입니다.
따라서 큰 직사각형의 면적을 구한 뒤, 작은 직사각형의 면적을 구해 빼주면 됩니다.

가로, 세로에서 각각 가장 긴 변의 길이를 구해줍니다. (maxH, maxV)
maxH, maxV를 곱하면 큰 직사각형의 넓이가 나옵니다.

그리고 maxH, maxV변에 해당하는 인덱스를 방문을 했다는 의미로 vis 배열을 true로 만들어줍니다.

    // 가로, 세로에서 가장 긴 변 구하기
    int maxH = -1, maxV = -1;
    int maxHIdx = -1, maxVIdx = -1;
    boolean[] vis = new boolean[6]; // false로 자동으로 초기화 됩니다. (프로그래머스에서는 가끔 수동으로 초기화 해야 통과되는 문제도 존재)
    for(int i=0; i<6; ++i) {
      Line cur = lines.get(i);
      if(cur.direction == 1|| cur.direction == 2) { // 가로인 경우 (동, 서)
        if(maxH < cur.len) {
          maxHIdx = i;
          maxH = cur.len;
        }
      } else { // 세로인 경우 (남, 북)
        if(maxV < cur.len) {
          maxVIdx = i;
          maxV = cur.len;
        }
      }
    }

    // 가로, 세로에서 가장 긴 변 방문처리
    vis[maxHIdx] = true;
    vis[maxVIdx] = true;

 

3. 작은 직사각형의 가로, 세로 구하기

 

 

4개의 변이 연속으로 vis 배열의 값이 false이면, 가운데에 있는 두 변이 작은 직사각형의 가로, 세로 변입니다.

따라서 if문으로 vis[i], vis[i+1], vis[i+2], vis[i+3]이 모두 false인 i를 찾는데, (i+n)이 6을 넘어갈 수 있으니, 모듈로 연산을 해줍니다.

그런 i를 찾으면, (i+1)%6, (i+2)%6의 두 변이 작은 직사각형의 변이 됩니다.

큰 직사각형 면적에서 작은 직사각형의 면적을 뺀 값을 출력해줍니다.

    // 작은 직사각형의 변 구하기 -> vis가 4연속 false라면, 가운데에 있는 두 변이 작은 직사각형의 변이다.
    int smallLen1 = 0, smallLen2 = 0;
    for(int i=0; i<6; ++i) {
      if(!vis[i] && !vis[(i+1)%6] && !vis[(i+2)%6] && !vis[(i+3)%6]) {
        smallLen1 = lines.get((i+1)%6).len;
        smallLen2 = lines.get((i+2)%6).len;
      }
    }

    System.out.println((maxH * maxV - smallLen1 * smallLen2) * K); // 답은 넓이 * K
  }

 

전체 코드

import java.io.*;
import java.util.*;

class Main {
  static int K; // 1 제곱 미터당 참외의 개수
  static ArrayList<Line> lines;
  static class Line {
    int len;
    int direction;

    Line(int direction, int len) {
      this.len = len;
      this.direction = direction;
    }
  }
  public static void main(String[] args) throws Exception {
    BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
    lines = new ArrayList<>();

    K = Integer.parseInt(br.readLine());

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

      int d = Integer.parseInt(st.nextToken()); // d는 방향을 의미합니다.
      int l = Integer.parseInt(st.nextToken()); // l은 변의 길이를 의미합니다.

      lines.add(new Line(d, l));
    }

    // 가로, 세로에서 가장 긴 변 구하기
    int maxH = -1, maxV = -1;
    int maxHIdx = -1, maxVIdx = -1;
    boolean[] vis = new boolean[6]; // false로 자동으로 초기화 됩니다. (프로그래머스에서는 가끔 수동으로 초기화 해야 통과되는 문제도 존재)
    for(int i=0; i<6; ++i) {
      Line cur = lines.get(i);
      if(cur.direction == 1|| cur.direction == 2) { // 가로인 경우 (동, 서)
        if(maxH < cur.len) {
          maxHIdx = i;
          maxH = cur.len;
        }
      } else { // 세로인 경우 (남, 북)
        if(maxV < cur.len) {
          maxVIdx = i;
          maxV = cur.len;
        }
      }
    }

    // 가로, 세로에서 가장 긴 변 방문처리
    vis[maxHIdx] = true;
    vis[maxVIdx] = true;

    // 작은 직사각형의 변 구하기 -> vis가 4연속 false라면, 가운데에 있는 두 변이 작은 직사각형의 변이다.
    int smallLen1 = 0, smallLen2 = 0;
    for(int i=0; i<6; ++i) {
      if(!vis[i] && !vis[(i+1)%6] && !vis[(i+2)%6] && !vis[(i+3)%6]) {
        smallLen1 = lines.get((i+1)%6).len;
        smallLen2 = lines.get((i+2)%6).len;
      }
    }

    System.out.println((maxH * maxV - smallLen1 * smallLen2) * K); // 답은 넓이 * K
  }
}

'Algorithm > 백준' 카테고리의 다른 글

[Java / 백준] 4781. 사탕 가게  (3) 2024.07.03
[백준 / Java] 2141. 우체국  (3) 2024.06.25
[백준 / Java] 14575. 뒤풀이  (0) 2024.06.18
[백준 / Java] 2665. 미로만들기  (2) 2024.06.11
[ 백준 / Java ] 2573. 빙산  (0) 2024.06.04