2012-05-10 3 views
9

분수를 나타내는 Objective-C 클래스를 만들고 있다고 가정하고, 변경 불가능한 버전과 변경 가능한 버전을 만들고 싶습니다.objective-c 클래스의 변경 불가능하고 변경 가능한 버전을 만드는 가장 효율적인 방법은 무엇입니까?

Foundation 프레임 워크의 패턴에 따라 변경할 수있는 버전에 fractionByAddingFraction:, 변경 가능한 버전에 addFraction: 메서드가 표시 될 것으로 예상 할 수 있습니다.

필자가 직면 한 패러독스는 두 클래스 사이에 한 번만 분수 추가 논리를 포함하는 방법입니다. 불변의 fractionByAddingFraction: 메서드는 코드 중복을 피하기 위해 변경 가능한 addFraction: 메서드에 대해 알아야하고 변경 가능한 메서드를 포함하는 것은 변경할 수없는 클래스에서 호출 될 수 있음을 의미합니다. 오브제는 그 요점을 무너 뜨린다.

간략한 설명 (또는 더 나은 여전히,이 단순화 된 예제의 연속)은 많이 감사하겠습니다!

+4

클래스 예제는 _value 오브젝트 _를 나타내는 것으로 보이므로 변경 가능한 버전을 제공해야한다고 생각하지 않습니다. __ 그냥 불변으로 만드십시오 .__ –

+0

@ Jordão이 특별한 예를 들어, 당신은 옳습니다. 나는이 개념이 전반적인 개념에 대한 혼란을 설명하는 가장 쉽고 가장 간결한 방법이라고 생각했다. (더 복잡한 클래스와 관련이 있기 때문이다.) 그것에 관계없이 어떻게 될지에 대한 생각? – user1385983

답변

3

당신의 접근 방식은 정확합니다 (실제적으로 필요하지 않는 한 당신이 피해야하는 가변적 인 서브 클래스가 정말로 필요한 경우). 혼란이 어디서 들어오고 있는지 명확하지 않습니다. addFraction:을 가장 쉽게 구현하려면 fractionByAddingFraction:을 사용하십시오. 그것은 약간 비효율적 일 것이지만 그것은 가장 합리적인 방향입니다. 그러나 일반적으로 당신은 아마 두 클래스가 사용하는 것이 어떤 개인 _GetInternalStuffByAddingInternalStuffs() 기능이보다 효율적으로 처리 할 것

- (void)addFraction:(Fraction *)anotherFraction { 
    Fraction *newFraction = [self fractionByAddingFraction:anotherFraction]; 
    self.internalStuff = newFraction.internalStuff; 
} 

:처럼 뭔가.

+0

제안 해 주셔서 감사합니다. 앞서 언급했듯이 모든 구성 요소가 변경 될 때마다 새 개체를 만드는 것이 비효율적 일 수 있기 때문에 첫 번째 방법을 피했습니다. 비공개 함수를 만드는 아이디어는 좋은 대안처럼 보입니다.하지만 두 클래스의 구현에 액세스 할 수있는 이상적인 위치를 궁금해하고 있습니다. 다른 곳에서는 액세스 할 수 없으므로 (헤더에 넣지 않을 수도 있습니다)? – user1385983

+0

이 작업은 일반적으로 Fraction + Private.h와 같은 개인 헤더로 수행됩니다. 이 유형의 경우 변경 가능한 양식을 버려야 할 수도 있습니다. NSNumber가 변경 가능한 양식을 가지고 있지 않음을 주목하십시오. 매우 빠르게 생성하지 않는 한, 값 객체의 단순성과 스레드 안전성이 매우 매력적입니다. 당신이 그들을 아주 빨리 만들지라도, 그것들 중 일부를 캐시 할 수 있습니다. NSNumber는 내가 기억하는 것처럼 정수 -1-12를 싱글 톤으로 캐시합니다. 불변 객체를 사용하면 가장 쉽게 캐싱 할 수 있습니다. 그러나 위의 내용은 변경 가능성이 필요할 때이를 처리하는 방법입니다. –

+0

http://opensource.apple.com/source/CF/CF-635/CFArray.c에서 기본 CoreFoundation 객체가 어떻게 구현되는지 살펴볼 수 있습니다. –

0

Foundation 컬렉션의 기본 구현은 속임수가됩니다. NSMutableFoo의 하위 클래스 인 구현이 하나 밖에 없으며 개인용 변경 플래그가 있습니다. 이는 클라이언트 코드가 특정 객체가 변경 가능한지 여부를 테스트 할 수 없지만 디버깅 및 어설 션을 제외하고는 결코 좋은 아이디어가 될 수 없다는 것을 의미합니다.

+0

정확하게 'NSFoo'는 'NSMutableFoo'의 하위 클래스가 될 것이고 'NSMutableFoo'는 두 클래스의 모든 메서드를 포함하지만, 변경 불가능한 하위 클래스의 'private 플래그를 기반으로하는 변경 가능한 클래스를 사용할 수있는 기능을 제한하겠습니까? – user1385983

+0

'NSFoo'는 NSMutableFoo'의 하위 클래스가 아닙니다. 관계는 일반적으로'NSFoo' ←'NSMutableFoo' ←'NSCFFoo'이며, 여기서'NSCFFoo'는 구체적인 구현입니다. 'NSCFFoo'의 변경 메소드는 변경 가능 플래그를 검사하고 변경 불가능한 경우 예외를 throw합니다. (실제로는 수신자 부담 브리징 때문에 실제보다 더 복잡합니다. CF가 포함되지 않으면 작동하는 방법입니다.) 자신의 클래스의 경우, 구체적인 서브 클래스를 'XYConcreteFoo'와 같은 것으로 부를 것입니다. –