https://school.programmers.co.kr/learn/courses/30/lessons/87390\

 

프로그래머스

SW개발자를 위한 평가, 교육의 Total Solution을 제공하는 개발자 성장을 위한 베이스캠프

programmers.co.kr

 


문제

문제 설명
정수 n, left, right가 주어집니다. 다음 과정을 거쳐서 1차원 배열을 만들고자 합니다.

n행 n열 크기의 비어있는 2차원 배열을 만듭니다.
i = 1, 2, 3, ..., n에 대해서, 다음 과정을 반복합니다.
1행 1열부터 i행 i열까지의 영역 내의 모든 빈 칸을 숫자 i로 채웁니다.
1행, 2행, ..., n행을 잘라내어 모두 이어붙인 새로운 1차원 배열을 만듭니다.
새로운 1차원 배열을 arr이라 할 때, arr[left], arr[left+1], ..., arr[right]만 남기고 나머지는 지웁니다.
정수 n, left, right가 매개변수로 주어집니다. 주어진 과정대로 만들어진 1차원 배열을 return 하도록 solution 함수를 완성해주세요.

제한사항
1 ≤ n ≤ 107
0 ≤ left ≤ right < n2
right - left < 105
입출력 예
n left right result
3 2 5 [3,2,2,3]
4 7 14 [4,3,3,3,4,4,4,4]


문제 해결을 위한 과정

 

이 문제의 핵심은 실제로 n * n크기의 2차원 배열을 선언하면 안 된다는 점입니다. n이 최대 10,000,000(10^7)이므로 실제로 배열을 만들면 시간 초과(TLE)가  발생합니다.

따라서 1차원 배열 상의 인덱스 값을 통해 2차원 공간의 행(row)과 열(col) 좌표를 수학적 접근을 통해 해결해야 합니다.

  1. 정답 배열 크기 설정: 잘라낼 구간의 길이는 right - left + 1이 됩니다. 이를 정수형으로 형변환하여 answer 배열을 만듭니다.
  2. 구간 순회: left부터 right까지 long 타입의 변수 i로 반복문을 돕니다.
  3. 2차원 좌표 유추 (몫과 나머지):
    • 행(row): i / n을 계산하면 해당 칸이 몇 번째 행에 있는지 알 수 있습니다. 문제에서는 1행부터 시작하므로 + 1을 해줍니다.
    • 열(col): i % n을 계산하면 몇 번째 열에 있는지 알 수 있습니다. 마찬가지로 1열부터 시작하므로 + 1을 해줍니다.
  4. 값의 규칙성 적용: 문제 그림을 분석해 보면 각 좌표에 들어갈 값은 Math.max(row, col), 즉 행 번호와 열 번호 중 더 큰 값이 채워진다는 규칙을 발견할 수 있습니다.
  5. 이를 answer 배열에 차례대로 담아 반환합니다.

특별히 봐야할 문법

 

long 타입을 이용한 큰 수 제어 및 형변환: left와 right는 자바의 기본 int 범위를 넘어설 수 있는 long 타입으로 주어집니다. 그렇기 때문에 루프 제어 변수 i 역시 long으로 선언해야 안전합니다. 다만 i / n과 i % n의 연산 결과는 최종적으로 n(최대 10^7)보다 작으므로 안전하게 (int)로 강제 형변환하여 배열 인덱스로 활용할 수 있습니다.

for(long i = left; i <= right; i++) {
    int row = (int)(i / n) + 1;
    int col = (int)(i % n) + 1;
}

소스코드
import java.util.*;

class Solution {
    public int[] solution(int n, long left, long right) {
        int[] answer = new int[(int)(right - left +  1)];
        int index = 0;
        
        for(long i = left; i <= right; i++) {
            int row = (int)(i / n) + 1;
            int col = (int)(i % n) + 1;
            
            answer[index] = Math.max(row, col);
            index += 1;
        }
        return answer;
    }
}

+ Recent posts