01. 유한을 넘어, 힐베르트의 무한 호텔 (Hilbert’s Hotel)
1. 학습 목표 (Learning Objectives)
- 수학자 힐베르트가 칸토어의 집합론을 방어하기 위해 비유한 기괴하고 소름 돋는 사고 실험, ‘무한 호텔의 역설(Hilbert’s paradox of the Grand Hotel)’을 살펴봅니다.
- 절대 끝나지 않고(Infinite) 메모리가 터지지 않으면서도 무한 명의 손님을 끊임없이 받아내는 파이썬의 핵심 내장 엔진 ‘제너레이터(Generator - yield)’ 의 로직을 실습합니다.
2. “방이 꽉 찼습니다만, 어서 오십시오!”
위대한 수학자 다비트 힐베르트는 일반인도 칸토어의 무한 개념을 직관적으로 느낄 수 있도록 재미있는 상상의 호텔을 지었습니다.
[상황 1] 힐베르트 호텔의 기본 설정 이 호텔에는 방 번호가 1호, 2호, 3호… 영원히 끝없이 이어지는 ‘무한 개의 방($\infty$)’이 존재합니다. 그런데 오늘 밤, 운이 나쁘게도 이 무한 개의 방마다 빠짐없이 손님이 가득 들어차서, ‘빈 방이 없습니다(Full)’.
이때, 새로운 여행객 1명이 지친 몸을 이끌고 힐베르트 호텔 로비로 들어옵니다. 일반적인 상식의 유한(Finite) 호텔이라면 “방이 꽉 차서 손님을 받을 수 없습니다”라고 하겠죠? 하지만 이 호텔 지배인은 웃으며 말합니다.
“물론 방은 꽉 찼지만, 당신이 체크인할 공간은 있습니다! 안내 방송을 하겠습니다. 지금 투숙 중인 모든 무한 명의 손님들은, 현재 자기 방 번호에 +1을 더한 다음 방으로 짐을 들고 이동해 주십시오!!”
[결과 분석]
- 1호실 손님 $\rightarrow$ 2호실로 이동
- 2호실 손님 $\rightarrow$ 3호실로 이동
- 100만 호실 손님 $\rightarrow$ 100만 1호실로 이동
- $\mathbf{n}$ 호실 손님 $\rightarrow$ $\mathbf{n+1}$ 호실로 영원히 이동!
방 끝이 무한하므로 밀려나는 손님은 절대 호텔 밖으로 쫓겨나지 않으며, 결과적으로 1호실은 완벽하게 텅 빈 상태가 됩니다! 새로운 여행객 1명은 당당히 1호실 키를 받아 들어갑니다. (무한 $\infty$ + 1 = 무한 $\infty$) 라는 기괴한 공식이 성립하는 순간입니다!
3. 파이썬 Generator 엔진으로 무한 호텔 코딩하기 (Python)
파이썬 프로그래밍 언어의 내부에는, 메모리 제한이나 숫자의 끝이 없이 값을 무한히 지연(Lazy Evaluation)시켜 찍어내는 마법의 키워드 yield(산출하다) 가 있습니다.
우리가 직접 파이썬으로 빈방이 영원히 마르지 않는 무한 호텔 매니저 수식을 짜보겠습니다!
import time
# 1. 파이썬 무한 호텔 제너레이터(Generator) 엔진 모듈
def hilberts_hotel_manager():
room_number = 1 # 1호실부터 시작
# while True: 절대 죽지 않고 멈추지 않는 영원한(무한) 우주 루프
while True:
# 일반 return과 다름! yield는 값을 던져주고 메모리를 그 상태로 '일시 정지'함.
# 다음 호출이 올 때까지 값을 보존하며 영원히 다음 방 번호를 만들어냅니다!
yield f"🔑 빈방 확보 완료! 당신은 [{room_number:05d} 호실]에 배정되었습니다."
room_number += 1 # 기존 투숙객 무한 밀어내기 연산 (n = n + 1)
# 2. 무한 호텔 시스템 가동
hotel_engine = hilberts_hotel_manager()
print("🏨 [힐베르트 무한 호텔 로비 시스템 가동]")
print("-" * 50)
# 1초에 한 명씩 새 손님이 찾아옵니다. 호텔방이 메모리 에러로 터지는지 지켜볼까요?
try:
current_guest_count = 1
# 💥 주의: 이 루프는 수만, 수억, 1조 명이 와도 절대 끝나지 않습니다!
# (본 실습에서는 10명만 보고 break로 멈춥니다)
while True:
print(f"[{current_guest_count:02d}번째 새 손님 도착!]")
# next() 함수: 무한 제너레이터 엔진을 찔러서 다음 yield 방 번호를 받아온다!
room_key = next(hotel_engine)
print(f"👉 {room_key}")
print("-" * 50)
current_guest_count += 1
time.sleep(0.5) # 0.5초 대기 렌더링
# 시뮬레이션 종료 조건 (10명만 받고 시스템 정지)
if current_guest_count > 10:
print("🚀 파이썬 무한 엔진은 수십억 명이 밀려와도 절대 오류(Memory Error) 없이 무한 yield를 가동할 수 있습니다!!")
break
except KeyboardInterrupt:
print("\n🛑 시스템 강제 종료.")
파이썬 무한 제너레이터 실행 렌더링:
🏨 [힐베르트 무한 호텔 로비 시스템 가동]
--------------------------------------------------
[01번째 새 손님 도착!]
👉 🔑 빈방 확보 완료! 당신은 [00001 호실]에 배정되었습니다.
--------------------------------------------------
[02번째 새 손님 도착!]
👉 🔑 빈방 확보 완료! 당신은 [00002 호실]에 배정되었습니다.
--------------------------------------------------
... (중략) ...
[10번째 새 손님 도착!]
👉 🔑 빈방 확보 완료! 당신은 [00010 호실]에 배정되었습니다.
--------------------------------------------------
🚀 파이썬 무한 엔진은 수십억 명이 밀려와도 절대 오류(Memory Error) 없이 무한 yield를 가동할 수 있습니다!!
보통의 리스트(List) 변수였다면 코딩 도중 방이 수억 개가 되는 순간 컴퓨터 메모리(RAM)가 펑 터지고 MemoryError가 뜹니다.
하지만 파이썬의 제너레이터(yield)는 과거의 값은 미련 없이 버리고, 오직 ‘다음 번호($n+1$)를 무한정 지연 창출해 내는 규칙성’ 하나만 달랑 뇌리에 들고 있으므로 무한(Infinity)을 완벽하게 코딩으로 다뤄낼 수 있습니다!
4. 학습 정리 (Summary)
- 무한의 역설 (+1 원리): 방이 꽉 찼어도 유한 세계에 없는 $n \rightarrow n+1$ 의 무한 밀어내기 시프트를 적용하면, $\infty$ 에 몇 명을 추가하든 그 덩어리 크기 속성은 변하지 않습니다.
- 파이썬 제너레이터(Generator): 파이썬에서 메모리를 박살 내지 않고 무한대 길이의 숫자나 연열을 취급할 때 고안된 알고리즘으로,
yield키워드를 통해 필요할 때마다 영원토록 힐베르트 방 번호를 뽑아낼 수 있는 IT의 핵심 기술입니다.