goodthings4me.tistory.com
파이썬 클로저(closure)
■ 클로저는 스코프에 묶인 변수를 바인딩 하기 위한 기술로, 파이썬에서 __closure__는 cell(셀)로 이루어진 튜플이며, cell 객체는 __closure__의 free variables(변수)를 저장하기 위해 사용되고, 각 cell에는 저장된 값을 확인할 수 있는 cell_contents라는 변수(속성)가 있다.
def closure_ex1():
x = 1
def inner():
y = 2
return x + y
return inner
r1 = closure_ex1()
print(r1, type(r1)) ## 리턴값은 inner 함수의 참조값
# <function closure_ex1.<locals>.inner at 0x0000023B36A21BF8> <class 'function'>
print(hasattr(r1, '__closure__')) ## r1에 속성 __closure__ 있는지
# True
print(r1.__closure__) ## int x의 위치는
# (<cell at 0x0000023B369D5FD8: int object at 0x00007FF9E5F79340>,)
print(type(r1.__closure__[0]))
# <class 'cell'>
for attr in dir(r1.__closure__[0]): ## 튜플의 res.__closure__[0] 속성들은
print(attr)
#__class__
#__delattr__
#__dir__
#__doc__
#__eq__
#__format__
#__ge__
#__getattribute__
#__gt__
#__hash__
#__init__
#__init_subclass__
#__le__
#__lt__
#__ne__
#__new__
#__reduce__
#__reduce_ex__
#__repr__
#__setattr__
#__sizeof__
#__str__
#__subclasshook__
#cell_contents
## 객체의 변수(속성)인 cell_contents
print(r1.__closure__[0].cell_contents) ## int x의 값은
# 1
print(r1()) ## 리턴된 함수의 실행
# 3
def closure_ex2(x, y):
x = x
y = y
def inner():
return x ** y
return inner
r2 = closure_ex2(2, 32)
print(r2)
# <function closure_ex2.<locals>.inner at 0x0000023B36A9C8C8>
print(r2.__closure__)
# (<cell at 0x0000023B36ACDD68: int object at 0x00007FF9E5F79360>, <cell at 0x0000023B36ACDD98: int object at 0x00007FF9E5F79720>)
for c in r2.__closure__:
print(c.cell_contents)
#2
#32
print(r2())
# 4294967296
def closure_ex3(x, y):
x = x
y = y
def inner(x, y):
return x ** y
return inner
r3 = closure_ex3(2, 32)
print(r3)
# <function closure_ex2.<locals>.inner at 0x0000023B36ABFAE8>
print(r3.__closure__)
# None
#print(r3())
# TypeError: inner() missing 2 required positional arguments: 'x' and 'y'
## closure_ex3 함수의 x, y 변수와 내부 inner 함수의 x, y 변수는 다름
print(r3(2, 32))
# 4294967296
## closure_ex3 내 inner 함수를 람다 함수로 변경
def closure_ex4(x, y):
x = x
y = y
return lambda x, y: x ** y
r4 = closure_ex4(2, 32)
print(r4)
# <function closure_ex4.<locals>.<lambda> at 0x0000023B36AD1048>
print(r4.__closure__)
# None
print(r4(2, 32))
# 4294967296
'코딩 연습 > 코딩배우기' 카테고리의 다른 글
파이썬의 삼항 연산자(Ternary Operator) (0) | 2020.11.11 |
---|---|
파이썬 크롤링(Crawling) - 셀레니움(Selenium) 연습 #2 (0) | 2020.11.10 |
파이썬 크롤링(Crawling) - 셀레니움(Selenium) 연습 #1 (0) | 2020.11.09 |
파이썬으로 아스키(ASCII) Code 출력, 그리고 영문자에 대한 진수값들 (0) | 2020.11.08 |
파이썬 크롤링(Crawling) 연습 - BeautifulSoup Documentation #2 (find_all, find, select 등) (0) | 2020.11.08 |
댓글