하나는 종종 불변 클래스는 다음과 같은 방법으로 매우 효율적으로 copyWithZone를 구현할 수 있다는 읽변경 가능한 하위 클래스가있는 불변 클래스의 경우 copyWithZone에서 [self retain]을 반환하는 것이 안전하고 좋은 방법일까요?
- (id) copyWithZone:(NSZone*)zone
{
return [self retain];
}
그 구현 뒤에 아이디어는 분명하다 : 는 원본과 사본 모두 불변의 인스턴스이며, 그들은 항상 정확히해야합니다 동일한 내용이므로 원본을 유지하고 복사 오버 헤드를 피하여 두 저장소가 동일한 저장소를 가리 키지 않는 이유는 무엇입니까?
그러나 변경 가능한 하위 클래스가 있으면 어떻게됩니까?
- (id) copyWithZone:(NSZone*)zone
{
MyClass* myCopy = [super copyWithZone:zone];
myCopy->myMember = [myMember copyWithZone:zone];
return myCopy;
}
그러나 이것은 위의 무엇을 의미 하는가 : 서브 클래스는 기본 클래스의 구현 세부 사항에 대해 걱정하지 않는 깨끗한 아키텍처와 의 가변 서브 클래스는이 방법으로 copyWithZone을 구현하기 위해 괜찮을 copyWithZone의 슈퍼 클래스 구현? 하위 클래스는 변경할 수 있으므로 여전히 사본은 변경할 수 없지만 원본은 변경할 수 있지만 하위 클래스 copyWithZone은 자체 유지 된 인스턴스에서 작동합니다. self 및 myCopy는 둘 다 동일한 인스턴스를 가리 킵니다. 따라서 나중에 mutableOriginal.myMember의 값을 변경하면 immutableCopy.myMember도 변경됩니다. 이는 일반적인 오류 일뿐입니다.
그래서 불변 클래스가 다음과 같은 방법으로 copyWithZone을 더 잘 구현하지 않아야합니까?
- (id) copyWithZone:(NSZone*)zone
{
if([[self class] isMemberOfClass:[MyBaseClass class]])
return [self retain];
else
{
MyBaseClass* myCopy = [[self alloc] init];
myCopy->myBaseMember = [myBaseMember copyWithZone:zone];
return myCopy;
}
}
아닙니다. 목록에있는 방법 중 하나를 따르는 '사본'을 구현해야한다고 생각하지 않습니다. 복사는 매우 내재적입니다. '[super copy]'를 호출하지 말고, 필요하다면 깨끗하고 새로운 인스턴스를 할당하는 것이 좋습니다. –