Gidhub BE Developer

객체와 인스턴스 객체의 이름공간

2018-02-04
goodGid

클래스 객체와 인스턴스 객체의 이름공간

  • 코드 작성 시 주로 발생하는 실수 중 하나가

    클래스 메서드 내에서 인스턴스(self)를 통하지 않고 변수에 접근하는 것이다.

  • 전역 영역의 변수와 클래스의 변수의 이름이 동일한 경우

    에러도 발생하지 않기 때문에 규모가 큰 프로그램에서는 이런 문제를 찾기가 쉽지 않다.

>>> str = "NOT Class Member"
>>> class GString:
...     str=""
...     def Set(self,msg):
...             self.str = msg
...     def Print(self):
...             print(str)          # self를 이용해 클래스 멤버에 적브하지 않는 경우
                                    # 이름이 동일한 전역 변수에 접근해서 출력함

>>> g = GString()
>>> g.Set("First Message")
>>> g.Print()
NOT Class Member


>>> class GString:
...     str=""
...     def Set(self,msg):
...             self.str = msg
...     def Print(self):
...             print(self.str)

>>> g = GString()
>>> g.Set("First Message")
>>> g.Print()
First Message

  • 위 예제에서는 전역 영역과 클래스 영역에 동일한 이름인 str이라는 변수가 존재한다.

  • 변수 이름이 같아도 다른 영역에 존재하기 때문에 당장은 문제가 되지 않는다.

    하지만 멤버 메서드인 Print() 내부에서 개발자의 실수로

    인스턴스 객체 self를 통하지 않고 전역 변수 str 값을 출력하고 있다.

  • 그렇기 때문에 의도와는 다르게 출력 결과는 전역 변수 str값이 출력된다.


  • 인스턴스 객체가 자신을 생성한 클래스 객체를 참조하기 위해

    파이썬에서는 인스턴스 객체의 내장 속성 ‘class‘가 있다.

  • 클래스 영역에 모든 인스턴스 객체에 공통된 데이터를 참조하기 위해 아래와 같이 사용한다.

>>> class Test:
...     data = "Ki yong"

>>> i2 = Test()
>>> i1 = Test()

>>> i1.__class__.data = " Good Gid "            # "__class__" 속성을 이용해 클래스 데이터를 변경
>>> print(i1.data)          # 참조하는 모든 인스턴스가 변경
 Good Gid 
>>> print(i2.data)
 Good Gid 

>>> i2.data = " Local Change "      # i2 인스턴스 객체의 데이터만 변경
>>> print(i1.data)
 Good Gid 

>>> print(i2.data)
 Local Change 
>>> print(i2.__class__.data)        # i2의 클래스 객체의 데이터는 변경되지 않음
 Good Gid 

  • 인스턴스 객체 ‘i2’의 이름공간에 멤버 변수 ‘data’를 변경하는 경우

    우선적으로 인스턴스 이름공간을 탐색하기 때문에 인스턴스 이름공간의 데이터를 출력한다.

  • 물론 인스턴스 객체에 동일 이름의 데이터가 존재하더라도

    __class__를 이용해 클래스 이름공간의 데이터에 접근할 수 있다.


Index