파이썬에서 객체 지향 디자인을 시작하고 싶으신가요? 파이썬의 __init__
메서드를 배워 첫걸음을 내딛어 보세요.
이 튜토리얼에서는 파이썬 클래스와 객체의 기초를 다룬 후, __init__
메서드에 대해 자세히 알아보겠습니다.
이 튜토리얼을 마치면 다음과 같은 질문에 대한 답을 얻을 수 있습니다.
- 인스턴스 변수 또는 인스턴스 속성이란 무엇인가?
__init__
메서드는 인스턴스 속성을 초기화하는 데 어떻게 도움을 주는가?- 속성에 대한 기본값은 어떻게 설정할 수 있는가?
- 클래스 메서드를 생성자처럼 사용하여 객체를 만들려면 어떻게 해야 하는가?
이제 시작해 봅시다.
파이썬 클래스와 객체
클래스는 파이썬에서 객체 지향 프로그래밍의 핵심입니다. 클래스를 만들어 데이터와 관련 기능을 묶고, 속성과 메서드를 정의할 수 있습니다.
클래스를 만들고 나면, 객체(인스턴스)를 생성하기 위한 설계도(또는 템플릿)로 사용할 수 있습니다.
👩🏫 예를 들어, 모든 객체가 다음 속성을 갖는 Employee
클래스를 만들어 보겠습니다.
full_name
: 직원의 전체 이름 (firstName lastName 형식)emp_id
: 직원 IDdepartment
: 소속 부서experience
: 경력 년수
이것은 무엇을 의미할까요? 🤔
각 직원은 Employee
클래스의 인스턴스 또는 객체가 됩니다. 그리고 각 객체는 full_name
, emp_id
, department
, experience
에 대한 자체 값을 갖습니다.
이러한 속성은 인스턴스 변수라고도 하며, 속성과 인스턴스 변수라는 용어는 같은 의미로 사용됩니다.
잠시 후 속성을 추가할 것입니다. 우선 다음과 같이 Employee
클래스를 만들어 보겠습니다.
class Employee: pass
pass
(자리 표시자)를 사용하면 스크립트를 실행할 때 오류를 방지할 수 있습니다.
Employee
클래스의 현재 버전은 크게 유용하지 않지만, 여전히 유효한 클래스입니다. 따라서 Employee
클래스의 객체를 만들 수 있습니다.
employee_1 = Employee() print(employee_1) #Output: <__main__.Employee object at 0x00FEE7F0>
다음과 같이 속성을 추가하고 값으로 초기화할 수도 있습니다.
employee_1.full_name="Amy Bell" employee_1.department="HR"
그러나 인스턴스 속성을 추가하는 이러한 접근 방식은 비효율적이며 오류가 발생하기 쉽습니다. 또한 클래스를 템플릿으로 사용하여 객체를 생성할 수 없습니다. 여기서 __init__
메서드가 유용하게 사용됩니다.
파이썬 클래스에서 __init__
메서드의 역할 이해
객체를 인스턴스화할 때 인스턴스 변수를 초기화할 수 있어야 하며, __init__
메서드가 이를 돕습니다. __init__
메서드는 클래스의 새 객체가 생성될 때마다 호출되어 인스턴스 변수의 값을 초기화합니다.
C++과 같은 언어로 프로그래밍한 경험이 있다면 __init__
메서드가 생성자와 유사하게 작동하는 것을 알 수 있습니다.
__init__
메서드 정의
Employee
클래스에 __init__
메서드를 추가해 보겠습니다.
class Employee: def __init__(self, full_name, emp_id, department, experience): self.full_name = full_name self.emp_id = emp_id self.department = department self.experience = experience
self
매개변수는 클래스의 인스턴스를 참조하며, self.attribute
는 인스턴스 속성을 오른쪽의 값으로 초기화합니다.
이제 다음과 같이 객체를 만들 수 있습니다.
employee_2 = Employee('Bella Joy', 'M007', 'Marketing', 3) print(employee_2) # Output: <__main__.Employee object at 0x017F88B0>
직원 객체를 출력할 때 직원 객체가 속한 클래스를 제외하고는 유용한 정보를 얻지 못합니다. 클래스에 대한 표현 문자열을 정의하는 __repr__
메서드를 추가해 보겠습니다.
def __repr__(self): return f"{self.full_name}, {self.emp_id} from {self.department} with {self.experience} years of experience."
Employee
클래스에 __repr__
을 추가하면 다음과 같습니다.
class Employee: def __init__(self, full_name, emp_id, department, experience): self.full_name = full_name self.emp_id = emp_id self.department = department self.experience = experience def __repr__(self): return f"{self.full_name}, {self.emp_id} from {self.department} with {self.experience} years of experience."
이제 직원 객체에는 유용한 표현 문자열이 있습니다.
print(employee_2) # Output: Bella Joy, M007 from Marketing with 3 years of experience.
몇 가지 규칙
더 진행하기 전에 몇 가지 참고 사항이 있습니다.
- 클래스 인스턴스 자체를 참조하기 위해
__init__
메서드의 첫 번째 매개변수로self
를 사용했고, 다양한 속성을 초기화하기 위해self.attribute_name
을 사용했습니다.self
를 사용하는 것이 선호되는 규칙입니다(다른 이름을 사용할 수 있음). __init__
메서드를 정의할 때 속성 이름과 일치하도록__init__
정의의 매개변수 이름을 설정합니다. 이는 가독성을 향상시킵니다.
속성에 대한 기본값을 추가하는 방법
지금까지 코딩한 예에서는 모든 속성이 필수입니다. 즉, 객체 생성은 모든 필드의 값을 생성자에 전달하는 경우에만 성공합니다.
경험 속성에 대한 값을 전달하지 않고 Employee
클래스의 객체를 인스턴스화하려고 합니다.
employee_3 = Employee('Jake Lee', 'E001', 'Engineering')
다음과 같은 오류가 발생합니다.
Traceback (most recent call last): File "main.py", line 22, in <module> employee_3 = Employee('Jake Lee','E001','Engineering') TypeError: __init__() missing 1 required positional argument: 'experience'
그러나 특정 속성을 선택적으로 만들고 싶다면 __init__
메서드를 정의할 때 해당 속성에 대한 기본값을 제공하여 그렇게 할 수 있습니다.
여기에서는 경험 속성에 대해 기본값 0을 제공합니다.
class Employee: def __init__(self, full_name, emp_id, department, experience=0): self.full_name = full_name self.emp_id = emp_id self.department = department self.experience = experience def __repr__(self): return f"{self.full_name}, {self.emp_id} from {self.department} with {self.experience} years of experience."
employee_3
객체는 경험 속성 값 없이 생성됩니다. 기본값 0은 경험에 사용됩니다.
employee_3 = Employee('Jake Lee', 'E001', 'Engineering') print(employee_3.experience) # Output: 0
클래스 메서드를 사용하는 대체 클래스 생성자
지금까지 우리는 __init__
메서드를 정의하고 필요할 때 속성에 대한 기본값을 설정하는 방법만 보았습니다. 또한 생성자에서 필수 속성 값을 전달해야 한다는 것도 알고 있습니다.
그러나 때때로 이러한 인스턴스 변수(또는 속성)의 값은 튜플, 사전 또는 JSON 문자열과 같은 다른 데이터 구조에서 사용할 수 있습니다.
그래서 우리는 무엇을 해야 할까요?
예를 들어 보겠습니다. 파이썬 사전에 인스턴스 변수의 값이 있다고 가정합니다.
dict_fanny = {'name': 'Fanny Walker', 'id': 'H203', 'dept': 'HR', 'exp': 2}
사전을 활용하여 다음과 같은 모든 속성을 얻을 수 있습니다.
name = dict_fanny['name'] id = dict_fanny['id'] dept = dict_fanny['dept'] exp = dict_fanny['exp']
그런 다음 다음 값을 클래스 생성자에 전달하여 객체를 만들 수 있습니다.
employee_4 = Employee(name, id, dept, exp) print(employee_4) # Output: Fanny Walker, H203 from HR with 2 years of experience.
기억하세요: 생성하는 모든 새 객체에 대해 이 작업을 수행해야 합니다. 이 접근 방식은 비효율적이며 확실히 더 잘할 수 있습니다. 하지만 어떻게?
파이썬에서는 클래스 메서드를 생성자로 사용하여 클래스의 객체를 만들 수 있습니다. 클래스 메서드를 생성하기 위해 @classmethod
데코레이터를 사용합니다.
사전을 구문 분석하고 인스턴스 변수 값을 가져와 직원 객체를 구성하는 데 사용하는 메서드를 정의해 보겠습니다.
@classmethod def from_dict(cls, data_dict): full_name = data_dict['name'] emp_id = data_dict['id'] department = data_dict['dept'] experience = data_dict['exp'] return cls(full_name, emp_id, department, experience)
사전의 데이터를 사용하여 객체를 생성해야 하는 경우 from_dict()
클래스 메서드를 사용할 수 있습니다.
💡 클래스 메서드에서 self
대신 cls
를 사용하는 것에 주목하세요. 인스턴스를 참조하기 위해 self
를 사용하는 것과 마찬가지로 cls
는 클래스를 참조하는 데 사용됩니다. 또한 클래스 메서드는 객체가 아닌 클래스에 바인딩됩니다.
따라서 클래스 메서드 from_dict()
를 호출하여 객체를 만들 때 Employee
클래스에서 호출합니다.
emp_dict = {'name': 'Tia Bell', 'id': 'S270', 'dept': 'Sales', 'exp': 3} employee_5 = Employee.from_dict(emp_dict) print(employee_5) # Output: Tia Bell, S270 from Sales with 3 years of experience.
이제 n명의 직원 각각에 대한 사전이 있는 경우 from_dict()
클래스 메서드를 생성자로 사용하여 사전에서 인스턴트 변수 값을 검색하지 않고도 객체를 인스턴스화할 수 있습니다.
📝 클래스 변수에 대한 참고 사항
여기서 우리는 개별 인스턴스가 아닌 클래스에 바인딩된 클래스 메서드를 정의했습니다. 클래스 메서드와 유사하게 클래스 변수도 가질 수 있습니다.
클래스 메서드와 마찬가지로 클래스 변수는 인스턴스가 아닌 클래스에 바인딩됩니다. 속성이 클래스의 모든 인스턴스에 대해 고정된 값을 가질 때 클래스 변수로 정의하는 것을 고려할 수 있습니다.
FAQ
1. 파이썬에서 __init__
메서드가 필요한 이유는 무엇입니까?
클래스 정의의 __init__
메서드를 사용하면 클래스의 모든 인스턴스의 특성 또는 인스턴스 변수를 초기화할 수 있습니다. __init__
메서드는 클래스의 새 인스턴스가 생성될 때마다 호출됩니다.
2. 파이썬 클래스에 여러 __init__
메서드를 사용할 수 있습니까?
파이썬 클래스에 여러 __init__
메서드를 갖는 목표는 객체를 인스턴스화하는 여러 생성자를 제공하는 것입니다. 그러나 여러 __init__
메서드를 정의할 수는 없습니다. 여러 __init__
메서드를 정의하면 두 번째이자 가장 최근의 구현이 첫 번째를 덮어씁니다. 그러나 @classmethod
데코레이터를 사용하여 객체를 인스턴스화하는 생성자로 사용할 수 있는 클래스 메서드를 정의할 수 있습니다.
3. 클래스에서 __init__
메서드를 정의하지 않으면 어떻게 됩니까?
__init__
메서드를 정의하지 않아도 객체를 인스턴스화할 수 있습니다. 그러나 인스턴스 변수를 수동으로 추가하고 각각에 값을 할당해야 합니다. 생성자에서 인스턴스 변수의 값을 전달할 수 없습니다. 이는 오류가 발생하기 쉬울 뿐만 아니라 객체를 인스턴스화할 수 있는 청사진으로 클래스를 갖는 목적을 무효화합니다.
4. __init__
메서드에서 인수에 대한 기본값을 가질 수 있습니까?
예, __init__
메서드를 정의할 때 하나 이상의 속성에 대한 기본값을 제공할 수 있습니다. 기본값을 제공하면 생성자에서 이러한 특성을 선택 사항으로 만드는 데 도움이 됩니다. 생성자에서 이러한 속성에 대한 값을 전달하지 않으면 속성은 기본값을 사용합니다.
5. __init__
메서드 외부에서 속성을 수정할 수 있습니까?
예, __init__
메서드 외부에서 속성 값을 항상 업데이트할 수 있습니다. 특정 인스턴스를 만든 후 새 속성을 인스턴스에 동적으로 추가할 수도 있습니다.
결론
이 튜토리얼에서는 __init__
메서드를 사용하여 인스턴스 변수의 값을 초기화하는 방법을 배웠습니다. 이는 간단하지만 특히 속성이 많은 경우 반복될 수 있습니다.
관심이 있다면 dataclasses 모듈을 탐색해 볼 수 있습니다. 파이썬 3.7 이상에서는 내장 데이터 클래스 모듈을 사용하여 데이터를 저장하는 데이터 클래스를 생성할 수 있습니다. __init__
및 기타 일반적으로 사용되는 메서드의 기본 구현 외에도 유형 힌트, 복잡한 기본값 및 최적화를 위한 멋진 기능이 많이 있습니다.
다음으로 파이썬에서 if __name__==’__main__’
에 대해 자세히 알아보겠습니다.