Computer Science/Python

파이썬 | 포인터와 참조

올리브한입 2024. 9. 22. 09:11
반응형

포인터와 참조는 메모리 주소와 객체에 대한 접근을 관리하는 방식으로, 주로 프로그래밍 언어에서 데이터 구조를 다룰 때 사용됩니다.

포인터란?

포인터는 특정 데이터의 메모리 주소를 저장하는 변수입니다. 포인터를 통해 데이터의 위치를 직접 참조하고 수정할 수 있습니다.

 

참조란?

참조는 변수나 객체를 가리키는 이름입니다. 즉, 실제 데이터가 있는 곳을 가리키는 "주소"와 같은 역할을 합니다. 하지만 직접 데이터가 아니라 그 데이터에 대한 접근 경로를 제공합니다.

 

예시

num1 = 11
num2 = num1

print("Before num2 value is updated:")
print("num1 =", num1)
print("num2 =", num2)

print("\nnum1 points to:", id(num1))
print("num2 points to:", id(num2))

num2 = 22

print("\nAfter num2 value is updated:")
print("num1 =", num1)
print("num2 =", num2)

print("\nnum1 points to:", id(num1))
print("num2 points to:", id(num2))
[Running] 
Before num2 value is updated:
num1 = 11
num2 = 11

num1 points to: 140196725320304
num2 points to: 140196725320304

After num2 value is updated:
num1 = 11
num2 = 22

num1 points to: 140196725320304
num2 points to: 140196725320656

 

  • num1과 num2는 처음에 모두 11을 가리킵니다. 이때 두 변수는 같은 메모리 주소를 참조합니다.
  • num2의 값을 22로 변경하면, 이제 num2는 새로운 값에 대한 참조를 가지게 되며, num1은 여전히 11을 가리킵니다. 따라서 두 변수는 서로 다른 메모리 주소를 참조하게 됩니다.
dict1 = {
    'value': 11
}

dict2 = dict1

print("\nBefore value is updated:")
print("dict1 =", dict1)
print("dict2 =", dict2)

print("\ndict1 points to:", id(dict1))
print("dict2 points to:", id(dict2))

dict2['value'] = 22

print("\nAfter value is updated:")
print("dict1 =", dict1)
print("dict2 =", dict2)

print("\ndict1 points to:", id(dict1))
print("dict2 points to:", id(dict2))

 

Before value is updated:
dict1 = {'value': 11}
dict2 = {'value': 11}

dict1 points to: 140196726505216
dict2 points to: 140196726505216

After value is updated:
dict1 = {'value': 22}
dict2 = {'value': 22}

dict1 points to: 140196726505216
dict2 points to: 140196726505216

 

  • dict1과 dict2는 동일한 사전을 참조합니다. 따라서 두 변수의 ID는 동일합니다.

  • dict2의 'value'를 22로 변경하면, dict1도 영향을 받습니다. 이는 두 변수가 같은 객체를 참조하기 때문입니다. 결과적으로 dict1과 dict2 모두 {'value': 22}로 업데이트됩니다.

 

dict3 = {
    'value': 33
}

print("\nBefore value is updated:")
print("dict1 =", dict1)
print("dict2 =", dict2)
print("dict3 =", dict3)

print("\ndict1 points to:", id(dict1))
print("dict2 points to:", id(dict2))
print("dict3 points to:", id(dict3))

dict2 = dict3

print("\nAfter value is updated:")
print("dict1 =", dict1)
print("dict2 =", dict2)
print("dict3 =", dict3)

print("\ndict1 points to:", id(dict1))
print("dict2 points to:", id(dict2))
print("dict3 points to:", id(dict3))
Before value is updated:
dict1 = {'value': 22}
dict2 = {'value': 22}
dict3 = {'value': 33}

dict1 points to: 140189746036480
dict2 points to: 140189746036480
dict3 points to: 140189746069888

After value is updated:
dict1 = {'value': 22}
dict2 = {'value': 33}
dict3 = {'value': 33}

dict1 points to: 140189746036480
dict2 points to: 140189746069888
dict3 points to: 140189746069888

 

dict2 dict3로 참조를 변경했기 때문에, dict1은 여전히 {'value': 22}을 유지하고, dict2는 이제 dict3과 동일한 값을 참조하게 됩니다.

 

만약 dict1도 dict3를 참조하게 된다면

dict1 = dict2
print("\nAfter dict1 is updated:")
print("dict1 =", dict1)
print("dict2 =", dict2)
print("dict3 =", dict3)

print("\ndict1 points to:", id(dict1))
print("dict2 points to:", id(dict2))
print("dict3 points to:", id(dict3))
After dict1 is updated:
dict1 = {'value': 33}
dict2 = {'value': 33}
dict3 = {'value': 33}

dict1 points to: 140326917734784
dict2 points to: 140326917734784
dict3 points to: 140326917734784

마지막으로 dict1 dict2와 동일하게 설정하면, dict1 dict3을 참조하게 됩니다. 이때 dict1, dict2, dict3의 ID를 확인하여 모든 참조가 동일한 객체를 가리키고 있는지 확인할 수 있습니다. 

이렇듯 원래 참조하던 {'value': 22} 객체의 참조 수가 하나 줄어듭니다. 이 객체를 참조하는 변수가 더 이상 없으면, Python의 가비지 컬렉터가 이를 인식하고 메모리에서 제거할 수 있습니다. 

반응형