Python 강좌 / 생성자·인스턴스 속성·클래스 속성 이해하기

인스턴스 속성은 객체별 데이터를, 클래스 속성은 클래스에서 공유하는 값을 표현합니다. 변경 가능한 리스트를 클래스 속성으로 두면 모든 객체가 같은 목록을 공유할 수 있으므로 객체별 상태는 초기화할 때 만듭니다.

속성 위치가 공유 범위를 정합니다

self.items는 해당 인스턴스에 저장한 속성입니다. class 본문에 items=[]를 두면 그 리스트는 클래스에 속하며, 인스턴스에 별도 속성이 없을 때 공통 속성을 참조합니다. 객체 하나에서 append하면 다른 객체에서도 바뀐 내용이 보일 수 있습니다.

관련 동작과 지원 조건은 생성자·인스턴스 속성·클래스 속성 이해하기 관련 공식 문서에서 확인할 수 있습니다.

불변인 기본 단위나 정책 이름은 클래스 속성으로 둘 수 있지만, 인스턴스에서 같은 이름에 대입하면 클래스 값 전체를 바꾸는 대신 해당 객체의 속성이 생길 수 있습니다. 조회와 대입의 위치를 함께 살펴보세요.

전체 예제와 실행 결과

별도의 실습 폴더에서 아래 파일을 UTF-8로 저장합니다. 가상환경을 선택한 터미널에서 python attributes.py 명령으로 실행합니다. macOS·Ubuntu에서 가상환경을 사용하지 않는 경우 명령 이름을 python3으로 바꿉니다.

attributes.py 파일의 전체 내용입니다.

class Ledger:
    currency = "KRW"

    def __init__(self, owner):
        self.owner = owner
        self.items = []

    def add(self, amount):
        self.items.append(amount)

a = Ledger("A")
b = Ledger("B")
a.add(3500)
print(a.items, b.items)
b.currency = "USD"
print(a.currency, b.currency, Ledger.currency)

예상 결과는 다음과 같습니다.

[3500] []
KRW USD KRW

생성자 인수와 상태 변경 계약

초기화 메서드에 필요한 값을 명시하면 유효한 객체의 조건을 알아보기 쉽습니다. 외부 리스트를 그대로 저장하면 호출자와 공유하므로 독립성이 필요하면 복사 여부를 정합니다. 단, 얕은 복사는 내부 객체를 공유할 수 있습니다.

클래스 속성을 설정값처럼 바꾸면 모든 인스턴스에 같은 영향이 간다고 단정할 수 없습니다. 예제의 b에는 자체 currency가 있어서 Ledger.currency를 나중에 바꿔도 b.currency는 USD를 유지합니다. 이런 동작이 복잡하다면 단위를 생성 인수로 고정하는 설계가 더 명확할 수 있습니다.

잘못된 공유를 재현하고 복구하기

  1. items=[]를 __init__ 밖 클래스 본문으로 옮기고 인스턴스의 self.items 대입을 제거합니다.
  2. a에 추가한 값이 b에도 보이는지 확인합니다.
  3. 원래대로 self.items=[]를 __init__에 두어 독립 상태를 복구합니다.

공유 목록이 필요한 경우도 있지만 의도적으로 설계하고 동시 접근과 수명까지 관리해야 합니다. 우연히 공유되는 클래스 목록을 전역 저장소처럼 사용하지 않습니다.