19회차 코딩테스트

2026-09-28 · Java 2문제 · SQL 2문제 · 3 PASS / 1 FAIL

FAIL 한 크레인 문제는 제출 코드 칸이 비어 있어 실패 원인을 단정하지 않았다. 나머지 세 문제는 제출 코드를 그대로 보존했다. 아래 로컬 검증은 프로그래머스 재채점 결과가 아니다.

19회차

나머지가 1이 되는 수 찾기

한 줄 요약n을 x로 나눈 나머지가 1이면 x는 n−1을 나누어떨어지게 한다. 답은 n−1의 약수 중 1을 뺀 가장 작은 것.

쉽게 말하면사탕 n개를 x명에게 똑같이 나눠 주고 1개가 남으려면, 1개를 빼 둔 n−1개가 딱 나눠떨어져야 한다.
PASS · 원문 기록2026.09.28 · 19회차

문제 원문 · 제출 코드

class Solution {
    public int solution(int n) {
        int answer = 0;
        for(int i=1;i<=n;i++){
            if(n%i==1){
                answer = i;
                break;
            }
        }
        return answer;
    }
}
  • i=1부터 시작해도 괜찮다 — n % 1은 항상 0이라 조건에 걸리지 않는다.
  • 처음 걸린 i에서 break 하므로 가장 작은 x가 답이다.
  • 가장 오래 도는 경우는 n−1이 소수일 때(약 n번). n ≤ 1,000,000이라 제한 안이다.
로컬 검증
3~50,000 전수 + 무작위 20,000 + 최악(n−1이 소수) 20개 → 70,020개 통과
기댓값: 에라토스테네스 체로 만든 "n−1의 가장 작은 소인수" 표 (제출 코드와 계산 방식이 다름)
19회차

크레인 인형뽑기 게임

한 줄 요약열은 고정하고 행을 위에서 아래로 내려가 처음 만난 인형 하나만 집는다. 바구니는 스택 — 맨 위와 같으면 둘 다 사라진다.

쉽게 말하면뽑기 기계의 크레인은 한 번에 하나만 집고, 바구니에서는 맨 위에 올려둔 인형만 보인다.
FAIL · 원문 기록2026.09.28 · 19회차

문제 원문 · 정답 풀이

제출 코드: 원문에 없음. FAIL 결과와 정답 풀이만 남아 있다. 아래는 "어디서 틀렸는가"가 아니라 "무엇을 알아야 풀 수 있는가"의 정리다.

Stack<Integer> basket = new Stack<>();
for (int m : moves) {
    int col = m - 1;                          // moves는 1부터 센 번호
    for (int row = 0; row < board.length; row++) {
        if (board[row][col] != 0) {
            int doll = board[row][col];
            board[row][col] = 0;              // 집은 자리는 비운다
            if (!basket.isEmpty() && basket.peek() == doll) {
                basket.pop();
                answer += 2;                  // 사라진 인형은 2개
            } else {
                basket.push(doll);
            }
            break;                            // 하나 집었으면 다음 명령으로
        }
    }
}
놓치기 쉬운 곳이유
m - 1사람 기준 1번 칸 → 배열 0번 인덱스
board[row][col] = 0비우지 않으면 같은 열을 다시 뽑을 때 같은 인형이 또 나온다
break없으면 그 열의 인형을 한 번에 전부 집는다. 공식 예제에서 break만 빼면 4가 아니라 6(비교용 시연)
answer += 2세는 것은 터진 횟수가 아니라 사라진 인형 수

basket.peek() == doll은 Integer와 int의 비교라 값을 풀어서(언박싱) 비교한다. 둘 다 Integer였다면 ==는 주소 비교다. 이 문제는 인형 번호가 100 이하라 캐시 범위 안에서 우연히 맞겠지만, 객체끼리는 equals가 안전하다.

오답노트의 개념 정리에는 배열과 ArrayList의 문법 차이도 있다 — arr.length vs list.size(), arr[i] vs list.get(i).

로컬 검증
공식 예제 = 4 (기대 4)
비교: break 를 뺀 형태는 같은 예제에서 6 — 한 번에 여러 개를 집는다
무작위 보드 20,000개 통과 (N 5~30, moves 1~1000)
기댓값: 열마다 인형을 ArrayDeque에 담아 두고 꺼내는 별도 시뮬레이션
19회차

어린 동물 찾기 (원문 제목: 이름이 있는 동물의 아이디)

한 줄 요약"어린 것"을 찾는 대신 "Aged가 아닌 것"으로 조건을 뒤집는다. <>는 "같지 않다".

쉽게 말하면늙은 동물만 빼고 나머지를 전부 고른다. 다만 상태가 비어 있는(NULL) 동물도 같이 빠진다.
PASS · 원문 기록2026.09.28 · 19회차

문제 원문 (어린 동물 찾기) · 제출 코드

기록 주의. 오답노트의 제목은 "이름이 있는 동물의 아이디"다. 하지만 그 문제는 18회차에서 이미 풀었고, 이번 제출 SQL(ANIMAL_ID·NAME 조회, INTAKE_CONDITION <> 'Aged', ID순)은 "어린 동물 찾기"의 요구사항과 정확히 일치한다. 제목 칸이 지난 회차 양식에서 남은 것으로 보고 공식 문제명을 썼다.

SELECT ANIMAL_ID, NAME
from ANIMAL_INS
where INTAKE_CONDITION <> 'Aged'
order by ANIMAL_ID;

<> 'Aged'는 INTAKE_CONDITION이 NULL인 행도 함께 뺀다. NULL과의 비교는 "알 수 없음"이라 WHERE를 통과하지 못한다. 이 문제는 해당 컬럼이 NOT NULL이라 상관없지만, NULL이 섞일 수 있다면 OR INTAKE_CONDITION IS NULL을 따로 적는다.

로컬 검증 (SQLite)
제출 SQL → A100|NULL, A300|보리, A400|두부     (Aged인 A200 제외)
<> 'Aged' 결과 3행 — INTAKE_CONDITION이 NULL인 A500도 빠짐
OR ... IS NULL 추가 → A100, A300, A400, A500
(비교) '이름이 있는 동물의 아이디' 정답 형태 → A200, A300, A400, A500
19회차

없어진 기록 찾기

한 줄 요약OUTS를 기준으로 외부 조인하고 INS 쪽이 NULL인 행만 남기면 "OUTS에만 있는 것"이 된다.

쉽게 말하면입양 명단 옆에 입소 명단을 나란히 붙였을 때, 옆 칸이 비어 있는 동물이 기록이 없어진 동물이다.
PASS · 원문 기록2026.09.28 · 19회차

문제 원문 · 제출 코드

SELECT O.ANIMAL_ID, O.NAME
from ANIMAL_INS I RIGHT JOIN ANIMAL_OUTS O ON I.ANIMAL_ID = O.ANIMAL_ID
where I.ANIMAL_ID is null
ORDER BY O.ANIMAL_ID;
  • INNER JOIN으로는 못 찾는다 — 짝이 없는 행은 조인 단계에서 이미 사라진다.
  • INS I RIGHT JOIN OUTS O = OUTS O LEFT JOIN INS I. 기준 테이블을 왼쪽에 두는 LEFT JOIN을 더 자주 쓴다. NOT EXISTS로도 같다.
  • SELECT는 O 쪽 컬럼. 짝이 없는 행의 I 쪽 컬럼은 전부 NULL이다.
  • 17회차 "있었는데요 없었습니다"는 양쪽에 다 있는 동물을 비교했다. 이번에는 한쪽에만 있는 동물을 찾는다.
로컬 검증 (SQLite)
제출 SQL                 → A700|해피, A900|누리
OUTS LEFT JOIN INS       → A700|해피, A900|누리
NOT EXISTS               → A700|해피, A900|누리
INNER JOIN + IS NULL     → 0행
SELECT I.ANIMAL_ID, I.NAME → NULL|NULL, NULL|NULL

로컬 검증과 범위

Java는 CodingTest19Test.java, SQL은 verify-sql19.mjs(Node 내장 SQLite 3.53, 메모리 DB)로 확인했다. SQL 파일을 그대로 읽어 실행한다. 여기서 쓴 문법과 NULL 비교 규칙은 MySQL·MariaDB와 같으며, 대소문자 비교·문자셋처럼 DB마다 다른 부분은 검사하지 않았다. 로컬 MariaDB 접속 정보는 쓰지 않았다.