-
Python - 함수에 배열을 인자로 전달할 때Python 2020. 12. 23. 17:35
함수에 배열을 전달할 때 무슨 일이 일어날까?
함수의 인자로 배열을 전달한 후에 배열에 5를 'append' 해보자.
def append_item(arr_in_function): print('id : ', id(arr_in_function), 'before change in function : ',arr_in_function) arr.append(5) print('id : ', id(arr_in_function), 'after change in function : ',arr_in_function) arr = [1,2,3,4] print('id : ', id(arr), 'before function : ', arr) append_item(arr) print('id : ', id(arr), 'after function : ', arr)
append_item이라는 함수에 인자로 arr라는 배열을 넘겼다.
함수 내에서는 arr_in_function에 5를 추가하는 과정을 거친다.
- 함수에 리스트를 전달하기 전
- 리스트가 함수에 전달된 후
- 함수 내에서 리스트에 5를 추가한 후
- 함수가 종료된 이후
각각의 상황에서 arr의 id를 조회해보면, 아래와 같이 id 값이 모두 동일하다는 것을 알 수 있다. 또한, 함수가 종료된 이후에도 arr에는 5가 여전히 추가되어 있다.
따라서, 함수에 배열을 전달하더라도, 배열을 구성하는 요소들이 모두 복사되어 전달되는 것이 아니라 배열의 값들을 가리키는 주소만 전달된 다는 것을 알 수 있다.
함수에 arr라는 배열을 가리키는 변수를 전달했을 때 함수 내에서 arr_in_function이라는 변수도 동일한 id값을 가리키게 된다.
함수 내에서 arr_in_function이 가리키는 배열에 5를 추가했다. 때문에, 함수가 종료되고 arr_in_function이라는 변수가 사라져도 arr는 여전히 5가 추가된 동일한 배열을 가리키고 있는 것이다.
함수의 인자로 배열을 전달한 후에 새로운 배열로 바꿔보자.
def append_item(arr_in_function): print('id : ', id(arr_in_function), 'before change in function : ', arr_in_function) arr_in_function = [10, 11, 12] print('id : ', id(arr_in_function), 'after change in function : ', arr_in_function) arr = [1,2,3,4] print('id : ', id(arr), 'before function : ', arr) append_item(arr) print('id : ', id(arr), 'after function : ', arr)
append_item이라는 함수에 인자로 arr라는 배열을 넘겼다.
함수 내에서는 arr_in_function에 새로운 배열을 할당해 주었다.
그 결과 이번에는 새로운 배열이 할당된 이후, arr_in_function의 id값이 변경되었으며, arr는 함수가 종료된 이후에도 변하지 않았다.(3번째 줄에서 id가 바뀌었고, 4번째 줄에서는 arr의 값이 그대로 남아있음을 확인할 수 있다.)
첫 번째 상황과 어떤 점이 달라진 것일까?
함수의 인자로 전달된 arr에 5라는 원소를 추가할 때는 arr와 arr_in_function이 동일한 주소를 가리키고, 그 주소가 가리키는 배열의 끝에 5가 추가되었다.
하지만, 이번에는 함수 내에서 arr_in_function에 새로운 배열을 넣어주었다. 따라서, arr_in_function은 이제 다른 배열을 가리키게 되었다. 이제 두 변수가 가리키는 주소가 달라졌기 때문에, arr_in_function을 아무리 변경해도 함수 밖의 arr에 영향을 끼치지 못한다.
reference - stack overflow link
추가 실험
여기까지가 Stack overflow에서 참고한 내용이다. 그렇다면, 배열을 arr[1:]과 같이 잘라서 함수에 전달한다면 어떻게 될까?
궁금해져서 직접 한번 실험해 보았다.
먼저 배열에 arr[1:]을 전달하고 숫자 5를 append해보았다.
def append_item(arr_in_function): print('id : ', id(arr_in_function), 'before change in function : ', arr_in_function) arr_in_function.append(5) print('id : ', id(arr_in_function), 'after change in function : ', arr_in_function) arr = [1,2,3,4] print('id of arr ',id(arr)) for i in range(len(arr)): print(f'id of arr[{i}:]',id(arr[i:])) print() print('id : ', id(arr), 'arr before function : ', arr) append_item(arr[1:]) print('id : ', id(arr[1:]), 'arr[1:] after function : ', arr[1:]) print('id : ', id(arr), 'arr after function : ', arr) print() for i in range(len(arr)): print(f'id of arr[{i}]',id(arr[i]))
아래와 같이 잘라서 함수에 전달하고, 5를 append했을 때, 짐작대로 arr는 변하지 않았다.
하지만, 여기서 특이한 점을 발견할 수 있었다.
1. 첫 번재 네모 박스 내의 id값이 모두 동일하다.
2. 함수 내의 arr_in_function과 함수 외부의 arr[1:]의 id가 동일하다. 그런데 함수 내부의 arr_in_function의 변경사항이 arr[1:]에는 반영되지 않는다.
id()
- Return the “identity” of an object. This is an integer which is guaranteed to be unique and constant for this object during its lifetime. Two objects with non-overlapping lifetimes may have the same id() value.
1번, 2번의 의문점을 해결해보자...
'Python' 카테고리의 다른 글
cPython [Deep Dive to Object] - 1 (0) 2021.04.21 Python - Variable Scope (0) 2021.01.06 Python - Call by Object Reference (1) 2020.12.26 Python? (0) 2020.12.21