Quick Comparison
class User:
def __init__(self, name: str) -> None:
self.name = name
@classmethod
def from_csv(cls, row: str) -> "User":
return cls(row.strip())
@staticmethod
def normalize(name: str) -> str:
return name.strip().title()| method가 알아야 할 대상 | 먼저 쓸 decorator | 용도 |
|---|---|---|
| 인스턴스 상태 | 일반 method | self를 통한 객체 동작 |
| class 자체·대체 constructor | @classmethod | cls 기반 생성·정책 |
| 어느 상태도 필요 없음 | @staticmethod 또는 module 함수 | 관련 utility |
문법
기본형은 인스턴스 메서드, 클래스 메서드, 정적 메서드 세 가지를 함께 보면 됩니다.
class Example:
def instance_method(self):
...
@classmethod
def class_method(cls):
...
@staticmethod
def static_method():
...메서드 선택
인스턴스 상태를 쓰면 일반 메서드 (self)
대부분의 메서드는 특정 객체 상태를 읽거나 바꾸기 때문에 self를 받는 인스턴스 메서드입니다.
class Counter:
def __init__(self) -> None:
self.value = 0
def inc(self) -> None:
self.value += 1이게 기준이고, classmethod와 staticmethod는 그 바깥의 특수한 경우입니다.
클래스 자체를 다루면 @classmethod
@classmethod는 첫 인자로 cls를 받습니다.
그래서 인스턴스 생성 규칙을 클래스 수준에서 정의할 때 유용합니다.
class User:
def __init__(self, name: str) -> None:
self.name = name
@classmethod
def from_csv(cls, row: str) -> "User":
return cls(row.strip())상속된 클래스에서도 cls가 맞게 전달되므로, 대체 생성자 패턴에 특히 자연스럽습니다.
상태를 안 쓰는 유틸이면 @staticmethod
@staticmethod는 self도 cls도 받지 않습니다.
클래스와 논리적으로 관련은 있지만 인스턴스/클래스 상태가 필요 없는 유틸 함수를 묶을 때 씁니다.
class User:
@staticmethod
def normalize(name: str) -> str:
return name.strip().title()굳이 클래스 안에 둘 필요가 없다면 모듈 함수가 더 나을 수도 있습니다.
구조 비교
애매하면 모듈 함수도 같이 검토한다
staticmethod가 항상 좋은 건 아닙니다.
클래스와 아주 강하게 묶이지 않는다면 그냥 모듈 함수가 더 읽기 쉬운 경우도 많습니다.
주의할 점
인스턴스 상태를 써야 하는데 @staticmethod로 만들면 self에 접근할 수 없습니다. 메서드 종류는 "어떤 상태를 쓰는가"로 결정해야 합니다.
# ❌ 인스턴스 속성을 써야 하는데 staticmethod 사용
class User:
def __init__(self, name):
self.name = name
@staticmethod
def greet():
return f"Hello, {self.name}"
# ✅ 인스턴스 메서드로 선언
class User:
def __init__(self, name):
self.name = name
def greet(self):
return f"Hello, {self.name}"참고 링크
2 sources