3.2.3 match 구문
Python 3.10 버전부터 새롭게 도입된 match 구문은 C, Java 등 다른 언어의 switch-case 문과 같이 기본적인 값 매칭 기능을 제공할 뿐만 아니라, 데이터의 ‘구조(형태)’까지 분해해서 매칭할 수 있는 훨씬 강력하고 현대적인 기능입니다. 처음에는 단순 값 매칭을 연습하고 후반부에서 구조적 패턴 매칭을 배웁니다.
기존 switch ~ case 구문과의 차별점
| 언어/구문 | 주요 특징 및 한계점 |
|---|---|
C/Java의 switch |
주로 정수형(int), 문자(char), 문자열(String) 등 단순한 단일 값의 일치 여부만 검사할 수 있습니다. 각 case마다 break를 명시하지 않으면 밑으로 주욱 누수(fall-through)되는 귀찮은 점이 있습니다. |
Python의 match |
숫자, 문자열 비교는 기본이고, 리스트 갯수, 튜플 내부의 변수 위치, 딕셔너리의 키 구조 등 복합 자료구조 자체를 분해(Unpacking)하여 매칭할 수 있습니다. break를 쓰지 않아도 매칭된 블록 하나만 실행되고 깔끔하게 종료됩니다. |
문법 및 키워드
구문에서 match와 case는 핵심 키워드입니다. C나 자바에 쓰이던 default: 키워드 대신 case _: (언더스코어) 문법을 기본값으로 사용합니다.
연산식 또는 변수 exp의 구조나 값을 각 case 블록의 패턴들과 위에서부터 순서대로 비교하고, 첫 번째로 구조/값이 일치하는 case를 찾으면 해당 case 내부 블록인 statements만 실행합니다.
어떤 case와도 일치하지 않으면 옵션인 case _: 이후의 블록을 실행한다.
match exp:
case value1:
statements
case value2:
statements
case _:
statements
exp:match구문에서 평가할 식(expression)이나 변수이며, 이 값이 어떤case와 일치하는지 확인value1,value2, …: 여러 개의 경우(case)를 정의하며,exp의 값과 각 경우를 비교statements: 각 경우에 해당하는 실행 문장이 정의되는 블록으로,exp의 값이 해당하는 경우, 해당 블록이 실행
예제
다음 구문 match 문장에서 value가 apple이므로 case 'apple'에 적용되어 출력 값은 사과이다.
value = "apple"
match value:
case 'apple':
result = "사과"
case 'banana':
result = "바나나"
case _:
result = "기타"
print(result)
출력:
사과
다음은 value가 banana이므로 result에 저장된 값은 바나나이다.
value = "banana"
match value:
case 'apple':
result = "사과"
case 'banana':
result = "바나나"
print(result)
출력:
바나나
다음은 mango로 비교할 값이 case에 없으므로 case _: 블록이 실행되어 None이 출력된다.
value = "mango"
match value:
case 'apple':
result = "사과"
case 'banana':
result = "바나나"
case _:
result = None
print(result)
출력:
None
고급 활용: 구조적 패턴 매칭 (Structural Pattern Matching)
(웹툰 비유: 미래 우체국의 최첨단 match 분류기입니다. 단순히 택배 상자의 주소(숫자)만 검사하는 옛날 기계(switch)와 달리, X-ray 눈으로 상자 내부의 ‘구조’와 ‘형태(리스트인지, 딕셔너리인지)’까지 단번에 꿰뚫어 보고 그에 맞는 전용 파이프로 슛! 하고 날려 보냅니다.)
match 구문의 진정한 강력함은 리스트나 딕셔너리 같은 복합 자료형의 내부 ‘구조’를 통째로 인식하여 분해(Unpacking)할 때 발휘됩니다. 값이 일치하는지 묻는 것이 아니라, “너는 리스트니? 튜플이니?” “요소가 2개니? 3개니?”라고 형태를 먼저 질문합니다.
(다이어그램:
match 터미널로 들어온 데이터들이 각자 자신의 형태([x, y], {"id": id}, _)에 맞는 X-ray 검사대(case)를 통과하며 곧바로 내부 변수로 분해(Unpacking)되어 처리되는 일련의 과정을 보여주는 애니메이션입니다.)
1. 리스트(List) 구조 언패킹 매칭
들어오는 데이터 리스트의 원소 개수와 위치에 따라 처리를 분기할 수 있습니다. 가장 놀라운 점은, 조건 판별에 통과함과 동시에 그 내부 값들을 x, y 같은 변수로 즉시 뽑아내어(Unpacking) 저장해 버린다는 것입니다.
# 2개의 요소가 들어있는 리스트
point = [10, 20]
match point:
case [0, 0]:
print("원점입니다.")
case [x, 0]:
print(f"X축 위의 점입니다. 위치 X = {x}")
case [0, y]:
print(f"Y축 위의 점입니다. 위치 Y = {y}")
case [x, y]: # point 리스트의 형태가 [요소1, 요소2] 와 일치하므로 여기에 진입!
# 진입과 동시에 x=10, y=20 으로 값이 자동으로 분해되어 할당됩니다!
print(f"일반 2차원 좌표: X={x}, Y={y}")
case [x, y, z]:
print(f"3차원 좌표입니다: X={x}, Y={y}, Z={z}")
case _:
print("단순 2차원 좌표가 아닙니다.")
출력:
일반 2차원 좌표: X=10, Y=20
2. 딕셔너리(Dictionary) 구조 검증 매칭
웹 API JSON 응답이나 게임의 상태 데이터와 같은 복잡한 딕셔너리 데이터에서, 필수 키(Key)가 존재하는지 마치 붕어빵 틀처럼 데이터 뼈대를 점검할 때 매우 깔끔한 코드를 작성할 수 있습니다.
response = {"status": 200, "data": "로그인 성공", "timestamp": "2023-10-27"}
match response:
# 딕셔너리 안에 status 값이 200이고, "data"라는 키가 있다면 통과!
# 그리고 그 "data" 키의 값을 즉시 msg 변수에 뽑아냅니다.
case {"status": 200, "data": msg}:
print(f"정상 처리됨: {msg}")
case {"status": 404}:
print("경고: 리소스를 찾을 수 없습니다.")
# 에러 코드가 무엇이든 error 키가 포함되어 있으면 통과!
case {"status": code, "error": err_msg}:
print(f"서버 오류 코드 {code}: {err_msg}")
case _:
print("알 수 없는 응답 포맷입니다.")
출력:
정상 처리됨: 로그인 성공
☕ Java vs 🐍 Python 스나이퍼 비교
1. Fall-through 방지 메커니즘
- Java:
switch문에서break;를 깜빡 잊고 적지 않으면, 의도치 않게 밑에 있는 다른case구문들까지 줄줄이 실행되는Fall-through버그가 매우 빈번하게 발생합니다. - Python:
match문은 오직 최초로 일치한 단 한 개의case블록만 실행하고 구문을 깔끔히 종료합니다.break명령어가 아예 필요하지 않습니다!
2. 매칭의 차원 (단일 값 vs 구조적 객체)
- Java (전통적): 정수, 문자, 짧은 문자열 등 단순한 기본 타입 데이터들의 “동등성(Equal)”을 비교하는 데 최적화되어 있습니다.
- Python: 데이터의 “구조와 형태(Shape)” 자체를 맞추는 만능 셰이프 매칭 퍼즐과 같습니다.
🎧 Vibe Coding
🗣️ 학생 프롬프트 (AI에게 이렇게 명령해 보세요): “파이썬 3.10 버전 이상의
match구문을 사용해서, RPG 게임 캐릭터의 장비 아이템 데이터를 분류하는 함수를 짜줘. 아이템이 무기인지 ([단검, 공격력 10]), 방어구인지 ([투구, 방어력 5, 20골드]), 아니면 알 수 없는 쓰레기인지 리스트의 길이와 형태 패턴 구조로 매칭하게 만들고 자세한 주석을 달아줘.”
코딩 영단어 학습 📝
match: 어울리다, 짝을 맞추다. (복잡한 데이터 퍼즐 조각이 어떤 뼈대 틀(Case)과 완벽하게 짝이 맞는지 맞춰보는 행위입니다.)case: 경우, 사례. (데이터가 들어맞을 수 있는 각각의 방(Room)이나 분류 통을 말합니다.)Unpacking (언패킹): 짐을 풀다. (구조적 패턴 매칭의 핵심입니다. 리스트나 딕셔너리라는 보따리가case틀을 통과하자마자 그 내부 내용물(짐)이 곧바로 풀려서 변수에 알맹이만 쏙 저장되는 마법 같은 기능입니다.)