[Python]property와 setter

변도진·2024년 5월 30일

Python

목록 보기
1/16
post-thumbnail

보다면 @property가 붙어있는 메소드를 심심치 않게 발견할 수 있다.
처음보면 무엇인지 몰라 당황할 것인데 이 property와 같이 쓰이는 setter에 대하여 알아보자.

property란 무엇인가?

property는 객체에 필드를 제어할 때에 쓰이는 클래스로 데코레이터와 같이 조합하여 쓰인다.
property로 데코한 메서드는 그 이름을 클래스의 필드처럼 사용할 수 있다.
property로 데코된 메서드는 클래스의 필드처럼 접근할 때 메서드를 실행한다.
흔히 생각하는 getter와 역할이 비슷하다.

예시

다음은 활용 예시이다.

class Student():
    def __init__(self, number) -> None:
        self._number = number # 학번
    
    @property
    def grade(self): # 학년
        return self._number // 1000
        
    @property
    def _class(self): # 반 
        return self._number % 1000 // 100
    
    @property
    def number(self): # 번호
        return self._number % 100

s1 = Student(3205)
print(f"{s1.grade}학년 {s1._class}{s1.number}번")

결과

3학년 2반 5번

학생 객체를 생성하면 학년, 반, 번호를 모두 따로 필드로 만들 수 있지만
학번만 필드로 만들고 property를 사용하여 학번으로부터 학년, 반, 번호를 따로 받을 수 있다.

setter란 무엇인가?

setter란 property의 의해 만들어진 필드를 초기화하기 위해 만들어진 property의 내부 메소드이다.
필드이름.setter로 데코한 메서드는 필드가 초기화될때 실행된다.
흔히 생각하는 setter와 비슷한 역할이다.

예시

다음은 활용 예시이다.

class Student():
    def __init__(self, number) -> None:
        self._number = number # 학번
    
    @property
    def grade(self): # 학년
        return self._number // 1000
        
    @property
    def _class(self): # 반 
        return self._number % 1000 // 100
    
    @property
    def number(self): # 번호
        return self._number % 100
    
    @grade.setter
    def grade(self, grade):
        if 1 > grade: # 범위 설정
            raise "학년이 1보다 작습니다." 
        self._number = (grade * 1000) + (self._class * 100) + self.number

    @_class.setter
    def _class(self, _class):
        if 1 > _class: # 범위 설정
            raise "반이 1보다 작습니다." 
        if 9 < _class:
            raise "반이 9보다 큽니다."
        self._number = (self.grade * 1000) + (_class * 100) + self.number

    @number.setter
    def number(self, number):
        if 1 > number: # 범위 설정
            raise "번호가 1보다 작습니다." 
        if 99 < number:
            raise "번호가 99보다 큽니다." 
        self._number = (self.grade * 1000) + (self._class * 100) + number


s1 = Student(3205)
print(f"{s1.grade}학년 {s1._class}{s1.number}번")
print(s1._number)

s1.grade = 5
print(f"{s1.grade}학년 {s1._class}{s1.number}번")
print(s1._number)

s1.grade = -1
print(f"{s1.grade}학년 {s1._class}{s1.number}번")

결과

3학년 2반 5번
3205
5학년 2반 5번
5205
Traceback (most recent call last):
  File "c:\workspace\study\python lab\property.py", line 48, in <module>
    s1.grade = -1
    ^^^^^^^^
  File "c:\workspace\study\python lab\property.py", line 20, in grade
    raise "학년이 1보다 작습니다."
    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
TypeError: exceptions must derive from BaseException

학년을 바꾸며 학번이 3000증가한 것을 학인 할 수 있다.
이처럼 property로 작성된 필드를 초기화 할때 setter가 작동한다.
초기화 값을 올바르게 설정하는데 사용될 수 있다.

정리

property -> getter
property.setter -> setter
이 것을 잘 사용해서 멋진 객채를 만들어보도록 하자.

참조

https://www.youtube.com/watch?v=nx0zHK0balQ
https://www.daleseo.com/python-property/

profile
낚시하고 싶다.

2개의 댓글

comment-user-thumbnail
2024년 5월 30일

아니 예외 처리 제대로 하라고요
ㅋㅋㅋㅋㅋㅋㅋ

1개의 답글