def parent_function(): def child_function(): print("this is a child function") child_function() parent_function() "this is a child function"
-> 중첩함수(nexted function) 혹은 내부 함수는 상위 부모 함수 안에서만 호출이 가능
-> child_function
은 parent_function
에서만 호출 가능
-> 중첩함수를 사용하는 이유는 아래와 같다
-> 함수 안의 반복되는 코드를 중첩함수로 선언하여 부모함수의 코드를 효과적으로 관리하고 가독성을 높일 수 있음
def print_all_elements(list_of_things): ## 중첩함수 선언 def print_each_element(things): for thing in things: print(thing) if len(list_of_things) > 0: print_each_element(list_of_things) else: print("There is nothing!")
-> 중첩 함수가 부모 함수의 변수나 정보를 가두어 사용하는 것
-> 부모 함수는 중첩 함수를 return함 => 부모 함수의 변수를 외부로부터 직접적인 접근을 격리하면서 중첩 함수를 통한 변수를 사용한 연산은 가능하게 함
-> 어떤 정보를 기반으로 연산을 실행하고 싶지만 기반이 되는 정보는 접근을 제한하여 노출이 되거나 수정이 되지 못하게 하고 싶을 때 사용함(주로 factory 패턴 구현 시)
** factory = 함수나 오브젝트를 생성해내는데 사용 됨
"input되는 수의 승 값 구하기" def generate_power(base_number): def nth_power(power): return base_number ** power return nth_power calculate_power_of_two = generate_power(2) calculate_power_of_two(7) >128 calculate_power_of_two(10) >1024 calculate_power_of_seven = generate_power(7) calculate_power_of_seven(3) >343 calculate_power_of_seven(5) >16907
* Decorator는 closure처럼 중첩함수를 return 하는 함수이며, 다른 함수에 적용해서,
적용된 함수가 실행되기 전에 무조건 실행됨(강제성 제공)
"덜 배운자의 코드덩어리" def welcome_decorator(func): def decorated(): print("Hello, ") func() return decorated @welcome_decorator def greeting(): print(" welcome to WECODE!") return greeting greeting()
-> 코드 발동 순서를 이해하지 못해서 입력값이 뒤집혔음
->return
은 정말 어려운 끝맺음code
다.
-> 결괏값은 두 줄이 나왔고, "Hello," 아랫줄에 "welcome to WECODE!"가 등장했다.
"이것이 코드다 실전편" def welcome_decorator(func): def wrapper(): return func() + "welcome to WECODE!" return wrapper @welcome_decorator def greeting(): return "Hello, "
->
wrapper
가 등장했다. 저언혀 기억해내지 못한 코드라 한숨만 나올 뿐
-> 그래도 다행히 입력값의 자리가 바뀌었다는건 깨달음
-> vscode 에 예제를 써놓고 몇가지 추가 예제들을 구글링해 이 값 저 값 대입해보며 또닥였더니, 그래도 많이 근접한 코드가 나왔다.
-> 아직까지 입력, 출력, 리턴값의 순서나 위치가 헷갈리고 중심이 잡히지 않은 것 같지만, repl 50번대 이후로 처음으로 내손내친 code
가 답에 근접했다고 하니, 조금은 뿌듯하다.
--> 하지만 역시 갈 길이 멀다. 주말에 다 제쳐두고 함수나 요소들의 정의, 기본 개념을 싹 다시 다져놔야 할 듯하다.
-> 어떤 객체(변수, 함수 등)가 유효한 범위
-> 범위 순서 = [Local Scope < Enclosed < Global < Built-in]
-> 주로 함수 안에서 선언된 변수나 함수가 local scope를 가짐
-> 중첩함수가 있을 때 적용되는 scope
-> 부모함수에서 선언된 변수는 중첩함수 안에서도 유효한 범위를 가지고 있음
-> 함수 밖에서 선언된 변수나 함수
-> 해당 변, 함수들은 해당 파일에서 선언된 지점 아래로는 다 유효한 범위를 가짐
-> 가장 광범위한 scope
-> 파이썬이 제공하는 함수 또는 속성들이 이 scope를 가짐
-> 따로 선언이 없어도 모든 파이썬 파일에서 유효한 범위를 가짐
ex> element 총 개수를 리턴하는 len
함수
-> 파이썬은 변수나 함수의 정의를 찾을 때, 다음 순서의 scope들 안에서 찾음
[Local => Enclosing => Global => Built-in]
-> 동일한 이름의 변수들이 서로 다른 scope에서 선언이 되면 더 좁은 범위에 있는 변,함수가 더 넓은 범위에 있는 변수를 가리는(shadowing) 효과가 나타남
"parameter 값에 상관 없이 무조건 "63"을 return 하기" "아마추어의 코드 뭉치" def scope_test(what_is_my_scope): number = 1 def inner_scope_test(what_is_my_scope): what_is_my_scope = 63 return number * what_is_my_scope return inner_scope_test(what_is_my_scope) "프로의 코드블럭" def scope_test(what_is_my_scope): what_is_my_scope = 63 def inner_scope_test(): return inner_scope_test return what_is_my_scope
-> 처음엔 곱셈을 할 생각을 않고 scope_test == 63
이라고 도배를 했지만 실패
-> 내부에 적용되는 변수랑 인자를 고정시키면 되는건가 싶어서 단순하게 1*63
구도를 만들어봄
--> 슨생님들의 고견을 여쭈었더니, 2줄이 줄어들었음
(근데 뭔가 내가 제일 처음 생각했던거랑 비슷하다. 문제는 그게 어떤식이었는지
지금은 기억이 나지 않는다는 것임)