[코드잇] 쉽게 배우는 파이썬 문법 - 프로퍼티(Property)

코드잇

안녕하세요, 온라인 코딩 스쿨 코드잇입니다.

​

이번 시간에는 파이썬에서 사용되는 프로퍼티(Property)라는 기능을 배워볼게요. 일단 프로퍼티가 무엇인지 배우기 전에 다음 코드를 살펴볼게요.

class Citizen:
    def __init__(self, age_value):
        self._age = age_value

    def get_age(self):
        print('나이를 리턴합니다.')
        return self._age

    def set_age(self, age_value):
        print('나이를 새로 설정합니다.')
        self._age = age_value

이 코드는 시민을 나타내는 Citizen 클래스입니다. Citizen 클래스는

- _age라는 나이를 나타내는 인스턴스 변수와

- get_age, set_age라는 인스턴스 메소드를 가지고 있는데요.

​

두 메소드를 살펴보니 get_age 메소드는 _age 의 값을 리턴하고, set_age 메소드는 _age의 값을 설정하네요. 여기까진 별로 어렵지 않죠? 여기서 왜 변수 이름을 그냥 age라고 하지 않고 굳이 맨 앞에 밑줄 하나를 붙여서 _age로 썼는지 궁금하실 분도 계실 텐데요. 그 이유는 파이썬의 캡슐화라는 것 때문입니다. 캡슐화는 클래스의 속성을 바깥에서 직접 접근하지 못하도록 하는 것인데요. 혹시 캡슐화가 무엇인지 자세히 알고 싶으신 분은 곧 코드잇에서 열릴 객체 지향 프로그래밍 수업을 참고해주세요.

​

당장 캡슐화를 몰라도 일단은 이 코드의 내용만 이해하시면 됩니다.

​

Citizen 클래스를 한번 사용해봅시다.

class Citizen:
    def __init__(self, age_value):
        self._age = age_value

    def get_age(self):
        print('나이를 리턴합니다.')
        return self._age

    def set_age(self, age_value):
        print('나이를 새로 설정합니다.')
        self._age = age_value


citizen = Citizen(20)
print(citizen.get_age())
citizen.set_age(25)
print(citizen.get_age())

이 코드를 실행하면

나이를 리턴합니다.
20
나이를 새로 설정합니다.
나이를 리턴합니다.
25

이렇게 잘 실행됩니다.

​

자, 이제부터 본격적으로 프로퍼티(Property)를 설명해드릴게요. 프로퍼티는 사실 데코레이터 함수입니다. 데코레이터가 뭔지는 이전에 2개의 게시글을 통해 설명해드렸는데요. 기억이 안 나시면 다시 아래 링크를 통해 글을 읽고 와주세요.

​

파이썬에서 데코레이터(Decorator)란??

파이썬 데코레이터(Decorator)에 파라미터 넣기

​

아래는 프로퍼티를 적용한 Citizen 클래스입니다. 코드를 보시죠.

class Citizen:
    def __init__(self, age_value):
        self.age = age_value

    @property
    def age(self):
        print('나이를 리턴합니다.')
        return self._age

    @age.setter
    def age(self, age_value):
        print('나이를 새로 설정합니다.')
        self._age = age_value

Citizen 클래스가 뭔가 좀 변했죠? 일단 get_age , set_age 메소드의 내용은 그대론데 그 헤더(header)들이 변했네요. 하나씩 살펴봅시다. 먼저 이 부분은 무슨 뜻일까요?

@property
def age(self):
    print('나이를 리턴합니다.')
    return self._age

이 함수의 바디(body) 부분은 get_age 의 바디와 같습니다. 같은데 그 헤더(header) 부분은 좀 특이하네요. 함수의 이름이 age 이고 그 위에 @property 이렇게 데코레이터 표시가 붙어있습니다. 이 @property가 우리가 배울 프로퍼티라는 겁니다.

​

저렇게 프로퍼티가 이름 위에 붙은 메소드는 조금 특이한 방식으로 기능이 변합니다. 일단 아래 코드처럼 프로퍼티가 적용된 Citizen 클래스를 한번 사용해볼까요?

class Citizen:
    def __init__(self, age_value):
        self._age = age_value

    @property
    def age(self):
        print('나이를 리턴합니다.')
        return self._age

    @age.setter
    def age(self, age_value):
        print('나이를 새로 설정합니다.')
        self._age = age_value


citizen = Citizen(20)
print(citizen.age)

맨 마지막 줄에

print(citizen.age)

이 부분은 age 라는 변수의 값을 출력하겠다는 뜻입니다. 그런데 지금 Citizen 클래스에는 _age 변수는 있어도 age 변수는 없습니다. 코드를 실행하면 에러가 날 것 같은데.. 한번 실행해볼까요?

나이를 리턴합니다.
20

어! 그런데 에러가 발생하지 않고 잘 실행됩니다. 그리고 그 결과를 보면 바뀌기 전의 Citizen 클래스의 메소드 중 이름 위에 @property 표시가 붙어있던 age 메소드가 실행된 것 같습니다. 사실 이것이 프로퍼티의 기능입니다.

​

Citizen 클래스의 내용 중 이 부분은

@property
def age(self):
  print('나이를 리턴합니다.')
  return self._age

이제

citizen.age 같은 코드를 실행할 때 새로운 의미를 부여한다는 뜻입니다. 원래 이 부분은

Citizen 이라는 인스턴스의 age 라는 변수의 값을 가져오겠다는 뜻이죠?

하지만 저렇게 age라는 함수 이름 위에 프로퍼티를 붙이면 citizen.age​ 코드의 의미가 Citizen 인스턴스의 age라는 메소드를 실행하겠다는 것으로 바뀝니다.

지금 age 메소드는 원래 있었던 get_age 메소드와 그 내용이 같습니다. 맨 처음 Citizen 클래스의 get_age 메소드와 바뀐 Citizen 클래스의 @property가 붙은 age 메소드를 비교해보세요. 바디가 같다는 걸 확인하실 수 있을 거에요.

@property 를 붙인 메소드는 일반적으로 어떤 인스턴스 변수에 대한 getter 메소드임을 나타냅니다.

그러니까 정리하자면

지금 age라는 메소드는 _age라는 인스턴스 변수의 getter 역할을 하는 메소드이고

원래 우리가 변수의 값을 가져올 때 사용하는 citizen.age 같은 구문이 프로퍼티(@property)로 인해 age메소드를 실행하는 걸로 의미가 바뀌어 실행된다는 겁니다.

프로퍼티를 처음 접하신 분은 이 원리가 굉장히 낯설 수도 있습니다. 앞으로 이 블로그에서 파이썬의 프로퍼티에 대해서 자세히 알려드릴게요. 일단 방금까지 설명드린 부분을 이해하고 익숙해지도록 노력해보세요. 그래야 다음 내용으로 넘어갈 수 있습니다. 아직 Citizen 클래스에서 이 부분

@age.setter
def age(self, age_value):
    print('나이를 새로 설정합니다.')
    self._age = age_value

의 의미는 설명드리지 않았는데요.

​

다음 게시글에서 이 부분의 의미와 프로퍼티를 왜 사용하는지를 알려드릴게요. 파이썬의 프로퍼티를 제대로 마스터하고 싶으시면 코드잇 블로그 구독 잊지마세요~!

​

​

기업문화 엿볼 때, 더팀스

로그인

/