클로저 사용하기

Tasker_Jang·2026년 2월 26일

1. 전역 변수 vs 지역 변수

전역 변수(Global Variable) 는 함수를 포함한 스크립트 전체에서 접근할 수 있는 변수입니다. 반면 지역 변수(Local Variable) 는 변수를 만든 함수 안에서만 접근할 수 있으며, 이 범위를 지역 범위(Local Scope) 라고 합니다.

# 전역 변수: 어디서든 접근 가능
x = 10

def print_x():
    print(x)  # 전역 변수 접근 가능

print_x()  # 10

# 지역 변수: 함수 안에서만 접근 가능
def make_local():
    y = 20   # 지역 변수
    print(y)

make_local()  # 20
# print(y)    # NameError: y는 함수 밖에서 접근 불가

2. global 키워드

함수 안에서 전역 변수의 값을 변경하려면 global 키워드를 사용해야 합니다. global을 선언하지 않으면 파이썬은 함수 안에서 새로운 지역 변수를 만드는 것으로 처리합니다.

count = 0

def increment():
    global count   # 전역 변수 count를 사용하겠다고 선언
    count += 1

increment()
increment()
print(count)  # 2

전역 변수가 없는 상태에서 global을 사용하면 해당 변수가 새로운 전역 변수로 생성됩니다.

def create_global():
    global new_var
    new_var = "저는 전역 변수입니다"

create_global()
print(new_var)  # 저는 전역 변수입니다

💡 네임스페이스(Namespace) 란 변수가 저장되는 공간입니다. locals() 함수로 현재 네임스페이스를 딕셔너리 형태로 확인할 수 있습니다.

def show_namespace():
    a = 1
    b = 2
    print(locals())  # {'a': 1, 'b': 2}

show_namespace()

3. nonlocal 키워드

함수 안에 또 다른 함수가 있을 때, 바깥쪽 함수의 지역 변수에는 읽기 접근은 가능하지만 값을 변경하려면 nonlocal 키워드가 필요합니다.

def outer():
    x = 10  # outer의 지역 변수

    def inner():
        nonlocal x   # 바깥쪽 함수의 지역 변수를 사용
        x += 1
        print(x)

    inner()  # 11
    print(x) # 11

outer()

nonlocal은 가장 가까운 바깥쪽 함수부터 변수를 찾습니다. 반면 global은 함수가 몇 단계로 중첩되어 있든 무조건 전역 변수를 가리킵니다.

키워드대상 변수탐색 방향
global전역 변수무조건 전역 범위
nonlocal바깥쪽 함수의 지역 변수가장 가까운 바깥쪽 함수부터 순서대로

4. 클로저(Closure)란?

클로저는 함수를 둘러싼 환경(바깥 함수의 지역 변수)을 기억하고 있다가, 나중에 함수를 호출할 때 그 환경을 다시 꺼내서 사용하는 함수입니다.

즉, return으로 반환되는 내부 함수가 참조하는 변수를 유지합니다.

바깥 함수가 종료된 이후에도 안쪽 함수가 바깥 함수의 변수를 계속 유지한다는 점이 핵심입니다.

def make_counter(start):
    count = start   # 바깥 함수의 지역 변수

    def counter():
        nonlocal count
        count += 1
        return count

    return counter  # 함수 자체를 반환

# make_counter가 종료되어도 count 값이 유지됨
counter_a = make_counter(0)
counter_b = make_counter(100)

print(counter_a())  # 1
print(counter_a())  # 2
print(counter_b())  # 101  ← counter_a와 독립적으로 동작

counter_acounter_b는 각각 독립된 환경을 유지합니다. 이처럼 클로저를 사용하면 프로그램의 흐름(상태)을 변수에 저장할 수 있습니다.


5. 람다로 클로저 간결하게 만들기

람다 표현식을 활용하면 클로저를 더 짧게 작성할 수 있습니다.

# def로 작성한 클로저
def make_adder(n):
    def adder(x):
        return x + n
    return adder

# lambda로 작성한 클로저 — 훨씬 간결
def make_adder(n):
    return lambda x: x + n

add_5 = make_adder(5)
add_10 = make_adder(10)

print(add_5(3))   # 8
print(add_10(3))  # 13

왜 기억할 수 있나?

일반적으로 함수가 끝나면 내부 변수는 사라지는데, 내부 함수가 외부 변수를 참조하고 있으면 파이썬이 그 변수를 __closure__ 라는 공간에 보관한다.

profile
ML Engineer 🧠 | AI 모델 개발과 최적화 경험을 기록하며 성장하는 개발자 🚀 The light that burns twice as bright burns half as long ✨

0개의 댓글