10.1 다 내 방식대로 할거야!
때때로 객체에 여러 다른 서비스 객체에 대한 많은 참조가 저장되어 있을 수 있어. 이런 참조들은 네트워크를 통해 전송하고 싶지 않거나 전송할 수 없는 것들이야: 파일, 데이터베이스 등에 대한 참조들.
이렇게 직렬화가 작동하도록 하려면 클래스가 스스로 직렬화를 관리할 수 있는 기능을 주기로 했어. 이를 위해 특별한 메소드들이 사용돼: __reduce__(), __getstate__(), __setstate__(). 이 메소드들은 객체가 어떻게 직렬화되고 복원되어야 하는지를 지정할 수 있게 해줘.
주요 관리 직렬화 메소드:
-
__reduce__(): 객체가 직렬화되는 방식을 지정해. -
__getstate__(): 직렬화를 위한 객체의 상태를 반환해. -
__setstate__(self, state): 상태에서 객체를 복원해.
아래에서 더 자세히 설명하고, 이들을 어떻게 함께 사용하는지 보여줄게.
10.2 메소드 __reduce__()
메소드 __reduce__()는 객체가 어떻게 직렬화되고 역직렬화되어야 하는지를 나타내는 튜플을 반환해. 튜플에는 보통 다음이 포함되어:
- 객체를 복원하는 데 사용할 함수나 클래스에 대한 참조.
- 이 함수나 클래스에 대한 인수의 튜플.
- 객체의 추가적인 상태 (필요한 경우).
예시:
import pickle
class CustomClass:
def __init__(self, value):
self.value = value
def __reduce__(self):
return (self.__class__, (self.value,))
def __repr__(self):
return f"CustomClass(value={self.value})"
# 객체 생성
obj = CustomClass(42)
# 객체 직렬화
serialized_obj = pickle.dumps(obj)
print("직렬화된 객체:", serialized_obj)
# 객체 역직렬화
deserialized_obj = pickle.loads(serialized_obj)
print("역직렬화된 객체:", deserialized_obj)
기본적으로 __reduce__() 함수는 다음과 같은 동작을 해:
class CustomClass:
def __init__(self, value):
self.value = value
def __reduce__(self):
# 클래스 정의
cls = self.__class__
# 생성자 인수
args = (self.value,)
# 객체 상태
state = self.__dict__
return (cls, args, state)
세 개의 객체로 구성된 튜플을 반환해:
현재 클래스에 대한 참조생성자 인수 (튜플)현재 객체 상태에 대한 참조
만약 이런 동작이 당신의 요구사항에 맞다면 __reduce__()를 재정의하지 않아도 돼.
10.3 상태 읽기 및 쓰기
메소드 __getstate__() 및 __setstate__()
이 메소드들은 직렬화 및 역직렬화 동안 객체의 상태를 관리하는 데 사용돼.
-
__getstate__(): 직렬화할 객체의 상태를 반환해. -
__setstate__(self, state): 상태에서 객체를 복원해.
예시:
모든 객체 필드를 저장하지 않고 몇몇 필드를 제외하고 싶다고 가정해보자. 이 경우 __getstate__() 메소드에서 다음을 수행해야 해:
- 현재 객체 상태(내부 필드
__dict__로 설정된 것을) 별도의 변수 - 딕셔너리state에 복사해. - 저장하지 않을 모든 필드를 삭제해.
__getstate__()함수의 결과로 얻은 객체를 반환해.
import pickle
class CustomClass:
def __init__(self, value):
self.value = value
self.internal_state = "internal"
def __getstate__(self):
state = self.__dict__.copy()
del state['internal_state'] # 내부 상태 제외
return state
def __setstate__(self, state):
self.__dict__.update(state)
self.internal_state = "restored internal" # 내부 상태 복원
def __repr__(self):
return f"CustomClass(value={self.value}, internal_state={self.internal_state})"
# 객체 생성
obj = CustomClass(42)
print("원본 객체:", obj)
# 객체 직렬화
serialized_obj = pickle.dumps(obj)
print("직렬화된 객체:", serialized_obj)
# 객체 역직렬화
deserialized_obj = pickle.loads(serialized_obj)
print("역직렬화된 객체:", deserialized_obj)
역직렬화 시, __setstate__() 함수에서 두 가지 작업을 수행해:
-
update()메소드를 사용하여 현재 객체 상태를 업데이트해. - 필드
internal_state(및 다른 비직렬화 필드)에 새 값을 할당해.
GO TO FULL VERSION