Python에서 클래스 메서드(class method)는 해당 클래스에 바인딩되는 메서드로, 클래스의 특정 인스턴스(객체)가 아닌 클래스 자체와 연결됩니다. 정적 메서드(static method) 역시 객체에 바인딩되지 않는다는 점에서 유사하지만, 몇 가지 중요한 차이점이 있습니다.
클래스 메서드를 정의할 때는 @classmethod 데코레이터를 사용하고, 정적 메서드를 정의할 때는 @staticmethod 데코레이터를 사용합니다.
클래스 메서드 문법
class my_class:
@classmethod
def function_name(cls, arguments):
# 함수 본문
return value
정적 메서드 문법
class my_class:
@staticmethod
def function_name(arguments):
# 함수 본문
return value
클래스 메서드와 정적 메서드의 차이점
| 클래스 메서드 (Class Method) | 정적 메서드 (Static Method) |
|---|---|
첫 번째 인수로 cls(클래스 자체)를 받습니다. |
특별한 첫 번째 인수를 받지 않습니다. |
| 클래스 상태(class state)에 접근하고 수정할 수 있습니다. | 클래스 상태에 접근하거나 수정할 수 없습니다. |
| 클래스를 매개변수로 받아 해당 클래스의 상태를 파악합니다. | 클래스 상태를 알지 못하며, 주로 매개변수를 받아 유틸리티 작업을 수행하는 데 사용됩니다. |
@classmethod 데코레이터를 사용합니다. |
@staticmethod 데코레이터를 사용합니다. |
일반적으로 정적 메서드는 독립적인 유틸리티 작업을 수행할 때 사용하고, 클래스 메서드는 팩토리 메서드(factory method)로 활용됩니다. 팩토리 메서드는 다양한 사용 사례에 맞춰 클래스 객체를 생성해 반환할 수 있습니다.
예제 코드
아래 예제는 직원(Employee) 클래스를 통해 두 메서드의 실제 동작을 보여줍니다. isAdult는 나이를 확인하는 정적 메서드이고, emp_from_year는 출생 연도로부터 직원 객체를 생성하는 클래스 메서드(팩토리 메서드)입니다.
from datetime import date as dt
class Employee:
def __init__(self, name, age):
self.name = name
self.age = age
@staticmethod
def isAdult(age):
if age > 18:
return True
else:
return False
@classmethod
def emp_from_year(emp_class, name, year):
return emp_class(name, dt.today().year - year)
def __str__(self):
return 'Employee Name: {} and Age: {}'.format(self.name, self.age)
e1 = Employee('Dhiman', 25)
print(e1)
e2 = Employee.emp_from_year('Subhas', 1987)
print(e2)
print(Employee.isAdult(25))
print(Employee.isAdult(16))
실행 결과
Employee Name: Dhiman and Age: 25 Employee Name: Subhas and Age: 31 True False
위 코드에서 Employee.emp_from_year('Subhas', 1987)처럼 클래스 메서드를 호출하면 별도의 생성자 로직 없이 출생 연도 기반으로 새로운 Employee 객체가 만들어집니다. 반면 isAdult는 클래스나 인스턴스의 상태와 무관하게 전달된 나이 값만으로 성인 여부를 판단하는 순수 유틸리티 함수 역할을 수행합니다.