질문의 역사
전통적인 객체 지향 프로그래밍에서 캡슐화는 내부 데이터에 대한 접근을 제한함으로써 구현됩니다. 대부분의 언어에는 엄격한 접근 수정자가 있습니다. 파이썬에서는 "우리는 모두 성인입니다"라는 원칙이 적용되며, 엄격한 비공식성이 없습니다.
문제
개발자들은 파이썬에서 보호된 (_protected) 및 비공식(__private) 속성 및 메서드를 혼동하며, "이중 밑줄"이 완전한 보호를 제공한다고 생각하거나 완전히 보호가 없다고 생각합니다.
해결
파이썬은 다음과 같은 규약을 구현합니다: 단일 밑줄 _var는 보호된 속성, 이중 밑줄 __var는 비공식적인 속성(이름 맹글링). 이러한 속성이나 메서드에 접근할 수 있지만 더 어렵습니다: _ClassName__var로 호출됩니다.
코드 예:
class Example: def __init__(self): self._protected = 1 # 보호됨 self.__private = 2 # 비공식적 (이름 맹글링) ex = Example() print(ex._protected) # 1 #print(ex.__private) # AttributeError print(ex._Example__private) # 2 (이름 맹글링)
주요 특징:
인스턴스를 통해 "비공식적인" 속성에 접근할 수 있습니까?
네, 맹글링을 통해 가능합니다: _ClassName__var. 그렇기 때문에 데이터에 접근할 수 있지만, 명시적이지 않습니다.
상속 시 비공식적인 메서드/속성이 어떻게 작동합니까?
이름 맹글링은 상속자가 부모의 비공식적인 요소를 우연히 재정의하는 것을 방해하지만, _ParentClass__attr을 통해 접근할 수 있습니다. 이중 밑줄이 있는 메서드는 자식 클래스 외부에서 "보이지" 않습니다.
class A: def __foo(self): print("A") class B(A): def bar(self): # self.__foo() — 오류 self._A__foo() # 작동함
파이썬에 JVM/C++ 수준의 완전한 비공식성이 있습니까?
아니요. 모든 것은 규약과 맹글링에 기반하고 있습니다. 데이터를 완전히 보호할 수는 없으며, 파이썬은 동적으로 모든 속성에 접근할 수 있도록 허용합니다.
대형 라이브러리에서 사용자가 비공식 속성을 이중 밑줄로 변경하려고 했는데, 이것이 "비밀"이라고 생각했지만, 여전히 _ClassName__var를 통해 변경이 발생했습니다.
장점:
단점:
프로젝트에서 내부 필드에 대해 단일 밑줄을 사용하고 클래스 외부에서 이를 건드리지 않도록 합의했습니다. 안전한 접근을 위해 프로퍼티를 추가했습니다.
장점:
단점: