[백준] PS/Java

[백준 2064] IP 주소 - JAVA

SH3542 2025. 5. 9. 23:40

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

 

1.

String[] ipByte = br.readLine().split("\\.");

 

regex에서 "."은 임의의 한 문자를 의미한다. 따라서, 모든 문자를 구분자로 사용하므로 빈 배열이 생성된다.

마침표 자체를 표시하기 위해 이스케이프 두 번 처리해준다.

 

2.

%32s : 왼쪽에 32 - s.len 만큼 공백 채움

%-32s : 오른쪽에 32 - s.len 만큼 공백 채움

 

항상 bit에서 0을 채워야하면 왼쪽이여서 몰랐었다. 해당 문제는 -를 붙여서 오른쪽을 채운다.

또한, 찾아보니 %S는 string을 uppercase로 표시해준다. %D는 없고 UnknownFormatConversionException을 던진다고 한다.

 

3.

32-m에서 m이 0이면, 2^32로 signed int 범위를 벗어난다.

해당 케이스가 있는진 확인 안했는데 long으로 쓰는게 낫다.

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;

class Main {

  public static void main(String[] args) throws IOException {

    BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
    int N = Integer.parseInt(br.readLine());

    // i번째 ip 주소의 j번 째 byte 값
    int[][] ip = new int[N][4];
    for (int i = 0; i < N; i++) {
      String[] ipByte = br.readLine().split("\\.");
      for (int j = 0; j < 4; j++) {
        ip[i][j] = Integer.parseInt(ipByte[j]);
      }
    }

    for (int m = 0; m < 33; m++) {
      int maskBits = 32 - m;

      // 네트워크 마스크 : 32 - m번째 까지 1을 채움 , 나머지는 0
      String mask = String.format("%-32s", Long.toBinaryString((1L << maskBits) - 1))
          .replace(" ", "0");

      // 네트워크 마스크를 byte 단위로 분리
      int[] maskByte = new int[4];
      int st = 0;
      for (int i = 0; i < 4; i++, st += 8) {
        maskByte[i] = Integer.parseInt(mask.substring(st, st + 8), 2);
      }

      boolean isAns = true;
      // 네트워크 주소 : 첫 ip 주소를 대표로, 네트워크 마스크와 & 연산한 값
      int[] adrByte = new int[4];
      for (int i = 0; i < 4; i++) {
        adrByte[i] = maskByte[i] & ip[0][i];
      }

      // 같은 네트워크(답)려면, 다른 모든 ip 주소에 대해서도 & 연산한 값이 같아야 함.
      for (int i = 1; i < N; i++) {
        for (int j = 0; j < 4; j++) {
          if ((maskByte[j] & ip[i][j]) != adrByte[j]) {
            isAns = false;
          }
        }
      }

      if (isAns) {

        System.out.println(String.format("%d.%d.%d.%d",
            adrByte[0], adrByte[1], adrByte[2], adrByte[3]));
        System.out.println(String.format("%d.%d.%d.%d",
            maskByte[0], maskByte[1], maskByte[2], maskByte[3]));

        break;
      }
    }
  }
}