goodthings4me.tistory.com
■ 클로저(Closure)는 함수를 만들어서 반환하는 함수 - 파이썬의 함수도 개체이기 때문에 가능
def maker1(m):
def inner(): # 함수 안에 정의된 함수(nested 함수)
print('closure ' * m)
return inner() # nested 함수 실행 후 반환
f1 = maker1(2) # closure closure
print(f1) # None
def maker2(m):
def inner():
print('closure ' * m)
return inner # nested 함수 반환
f2 = maker2(3) # print 함수 실행 X
f2() # closure closure closure --> print('clouser ' * m) 실행, m의 값 참조
print(f2) # inner 함수 리턴 확인(함수 오브젝트 리턴)
# <function maker2.<locals>.inner at 0x000001F08EC25C80>
# 이때, 매개변수 m은 maker 함수 안에서 선언된 변수이고, 실행이 종료된 함수(maker)의 변수는 소멸되는 것이 정상인데, 어디에 있을까?
# 이렇게 함수의 안쪽에 위치한 함수(nested func)가 자신이 필요한 변수의 값을 어딘가에 저장해 놓고 호출 시 참조하는 테크닉을 "클로저(Clouser)"라 한다.
※ 변수값 m의 위치는?
print(type(f2)) # <class 'function'>
print(dir(f2)) # '__closure__'
print(f2.__closure__) # (<cell at 0x000001F08E83D7F8: int object at 0x00007FF8DF8B9380>,)
print(type(f2.__closure__)) # <class 'tuple'>
print(f2.__closure__[0])
# <cell at 0x000001F08EBE1678: int object at 0x00007FF8DF8B9380>
print(dir(f2.__closure__[0])) # 'cell_contents'
print(f2.__closure__[0].cell_contents) # 3
# 변수 m의 값의 위치는 __clouser__의 인덱스 0의 위치에 저장된 객체의 변수(속성)인 cell_contents에 있다.
※ 변수 2개인 경우는?
def maker3(m, n):
def inner():
print(n * m)
return inner
f3 = maker3(4, 'Closure')
f3() # ClosureClosureClosureClosure
print(f3.__closure__)
# (<cell at 0x000001F08EBE1E28: int object at 0x00007FF8DF8B93A0>,
# <cell at 0x000001F08ECAD048: str object at 0x000001F08E838B90>)
print(f3.__closure__[0].cell_contents) # 4
print(f3.__closure__[1].cell_contents) # Closure
# 변수는 __closure__의 인덱스에 저장됨
※ 클로저(Closure) 응용
def outer(tag):
tag = tag
def inner_html(text):
contents = text
print('<{0}>{1}<{0}><br/>'.format(tag, contents))
return inner_html
p_tag = outer('h2')
p_tag('파이썬 중첩함수(Nested Func)와 클로저(Closure)')
[실행 결과]
<h2>파이썬 중첩함수(Nested Func)와 클로저(Closure)<h2><br/>
[참고 자료] 윤성우의 열혈파이썬 중급편
'코딩 연습 > 코딩배우기' 카테고리의 다른 글
[python] 파이썬 스태틱(static) 메서드와 클래스(class) 메서드 (0) | 2020.09.17 |
---|---|
[python] 파이썬 데코레이터 (Decorator) (0) | 2020.09.16 |
[python] 파이썬 property객체, @property 데코레이터 (0) | 2020.09.14 |
[python] 파이썬 __slots__의 효과 (0) | 2020.09.14 |
[python] 파이썬의 정보은닉(Information Hiding)과 __dict__ 메서드에 대해 (0) | 2020.09.13 |
댓글