2010-04-18 4 views
1

objective-c 런타임에는 class_createInstance와 같은 객체를 직접 생성 할 수있는 함수가 있다는 것을 알고 있습니다. 내가 알고 싶은 것은 루트 클래스 (NSObject) alloc 메서드가 아닌 다른 함수가 실제로 사용된다면 말입니다. 나는 KVC 바인딩과 같은 것들을 생각하지만, 그것들은 아이폰 OS에 존재하지 않는다. (내가 잘못하면 내 지식을 수정해라.) 이렇게 할 수있는 것이 있는가?목표에있는 객체가 -c alloc을 거치지 않고 생성 되었습니까?

궁금한 점이 있으시면 클래스에 ivars를 선언하지 않고 objc 런타임을 우회하는 방식으로 인스턴스의 크기를 할당하려고합니다. + alloc 메서드를 재정의하고 class_createInstance (자기, 마디의 바이트 수).

감사

편집 나는 좀 더 구체적으로해야한다고 생각. 런타임에 클래스를 런타임에 추가하고, 아마도 같은 클래스의 변경된 버전을 언로드하고 다시로드합니다. 나는 class_addMethod와 같은 것들 때문에 대부분의 이슈들을 해결해 왔지만 클래스가 등록 된 후에는 ivars에 해당하는 것이 없다. 내가 생각할 수있는 두 가지 해결책은 런타임과 관련하여 실제 ivars가 없다는 것입니다. 그러나 alloc을 오버라이드하여 extraBytes를 통해 충분한 공간을 확보하는지 확인하거나 또는 실제 ivars에 대한 포인터 인 ivar을 대신 선언합니다 , 나는 내가 원하는 것을 무엇이든 할 수있다. 이전 전략을 사용하는 것을 선호하지만 무언가가 오버로드 된 alloc 메소드를 거치지 않고 객체의 인스턴스를 할당하는 경우와 같이 잘못 될 수있는 여러 가지가 있습니다. 누구든지 이런 것들을 알고 있습니까?

답변

1

안전하지 않은 기존 클래스의 동작을 변경하려는 경우 또는 NSObject의 직접 하위 클래스 인 사용자 지정 클래스에 대해 무언가를하려고 할 때 확실하지 않습니다.

실제로 표시되는 거의 모든 NSString은 개인 서브 클래스의 인스턴스이며 해당 서브 클래스는 문자열에 대한 공간을 오브젝트와 인라인으로 할당합니다.마찬가지로 char *에 대한 포인터를 포함하는 대신 문자 데이터는 개체의 ivars 바로 뒤에옵니다. 이 같은 목적으로 extraBytes 매개 변수가 NSAllocateObject(Class aClass, NSUInteger extraBytes, NSZone *zone)에 있습니다.

한편, 그렇습니다. 그런 속임수를 쓸 수 있습니다. 다른 한편으로는 에 대해 알고 있어야합니다. NSString의 프라이빗 서브 클래스 (프라이빗 클래스이므로 런타임 인트로 스펙을 통해 만 상호 작용할 것입니다)와 같은 것을하려고하면 아마 충돌 할 것입니다.

이와 비슷한 기능을하는 공개 코코아 클래스가 몇 개 있기 때문에 클래스가 NSObject에서 직접 상속하는 것이 가장 좋습니다. NSLock은 하나입니다. NSLock의 사용자 정의 하위 클래스에 대한 메모리의 레이아웃은 { isa, <ivars of NSLock> <ivars of subclass of NSLock> <more NSLock stuff, space reserved using the extraBytes parameter> }입니다.

또한, + alloc calls + allocWithZone : 및 + allocWithZone :이 더 일반적인 무시 점입니다.

+0

오,하지만 방금 한 일을 보았습니다. 좋아요, 재미있게 놀아도 괜찮습니다.하지만 실제로 사용하려고하지는 않습니다. 그것은 당신이 후회하고 당신이 방금 그것을 빨아 들여 그것을 정상적인 방식으로 해주기를 바랄만한 종류의 해킹입니다. 프레임 워크에서 범용 해킹을 사용하는 것이 좋을 것입니다. 프레임 워크에서는 gc가 전화기에 추가 된 경우 올바르게 가비지 수집에 적응할 수 있습니다. 당신은 ivars to ivars 일을 할 수도 있고, objc_getAssociatedObject/objc_setAssociatedObject를보고 싶을 수도 있습니다. 이것들은 기본적으로 객체에 여분의 내용에 대한 사전이있는 것을 자동화합니다. – Ken

+0

다른 한편, 컴파일/실행/디버그주기를 단축하고 앱에서 제공하는 내용이 사용되지 않으면 재미 있고 재미있게 들립니다. :-) ZeroLink, 를보고 싶을 지 모르지만. 이것은 개발 속도를 높이기위한 것이었고 당신이 설명하고, 코드를 다시로드하는 등의 작업을했습니다. 애플은 그걸 포기했지만 이상한 문제에 대한 해결책은 "제로락 끄기"였다. – Ken

+0

나는 이것을 allocWithZone :과 NSLock 예제에 대해 투표했습니다. 그러나 allocWithZone을 통해 호출하지 않는 항목을 충족시키지 못하기 때문에이 사실을 아직 받아 들일 수 없습니다. 또한 이것은 프로덕션 코드의 기초가 될 것이므로 NSLock 예제로 인해이 방법을 사용하지 않을 것입니다. 결국이 기술을 사용하는 NSLock 하위 클래스가 깨지게됩니다. –

0

나는 당신이 제안하고 무엇 싶어 왜 확실하지 않다 - 당신이 그것을 할 수있는 이유가 없지만, this post에 따르면, 일반적으로 사용하는 이유가 없습니다 class_createInstance 직접 (나는 그것을 특별히 사용하는 것에 대해서는 모른다). class_createInstance은 메모리 영역 또는 alloc에서 사용되는 다른 가능한 최적화도 고려하지 않습니다. 당신이 당신의 ivars를 숨기고있는 것을 시도하는 경우에, better ways가있다.

편집 : 나는 (이름에서 알 수 있듯이) 클래스에 ivar를 동적으로 추가하는 class_addIvar 함수를 찾고 있다고 생각합니다. 새 런타임에서만 작동하므로 시뮬레이터에서는 작동하지 않지만 iPhone에서는 작동합니다.

EDIT 2 : 아직 명확하지 않은 경우에만 allocWithZone을 항상 호출 할 수 있습니다. 기본 코코아 클래스 (예 : NSStringNSArray)는 allocWithZone을 재정의합니다. class_createInstance은 런타임 수준을 제외하고는 거의 사용되지 않으므로 클래스에서 사용하는 코코아 부분에 대해 걱정할 필요가 없습니다. 따라서 원래의 질문에 대한 대답은 "아니오"입니다 (또는 더 구체적으로는 alloc없이 객체가 생성되지만, 적어도 알고있는 한 allocWithZone이없는 객체는 생성되지 않습니다).

+0

문서를 조금 더 자세히 읽으면 ivars를 추가하는 것이 클래스가 할당 된 시점과 등록 된 시점 사이에서만 발생할 수 있음을 알 수 있습니다. 질문에서 나는 다른 ivars 같은 같은 클래스의 변수를로드/언로드 할 수 있어야한다고 지정합니다. 클래스를 런타임에서 언로드하거나 대체 할 수는 없습니다. –

+0

죄송합니다. 나는 그것을 보지 못했습니다. 원래의 질문에 답하기 위해서'allocWithZone'이 항상 호출 될 것이라고 가정하는 것이 안전합니다. - NSArray와 NSString과 같은 많은 기본적인 Cocoa 클래스가 클래스 클러스터로 구현되고' allocWithZone'. 또한, 도움이 될 경우 일반적으로'class_createInstance' 대신'NSAllocateObject'를 호출합니다 (실제로 정확한 차이는 확실하지 않습니다). – shosti

+0

NSAllocateObject는 class_createInstance를 호출합니다. 모든 NS * 함수는 Objective-C 런타임 함수를 래핑합니다. – rpetrich

-1

기술적으로는 alloc을 무시하는 것을 막을 수있는 방법이 없습니다. 그냥 + alloc이라는 클래스에 메소드를 생성하면된다. 나는 왜 네가해야 할 지 아무 이유도 상상할 수 없다.

-1

메모리를 관리하기가 너무 힘듭니다. 객체를 만들 때 OS가 동적으로 메모리를 할당하도록하십시오. 너무 많이 사용하면 OS가 한계에 가까워지고 있다는 알림을 보냅니다. 그 시점에서 당신은 더 이상 필요없는 것들을 dealloc 할 수 있습니다.

트릭을 사용해야하는 많은 메모리가 필요하다면 iPhone OS의 둥근 구멍에 사각형 디자인을 맞추는 대신 코어 레벨에서 다시 생각해 볼 필요가 있습니다.

제공하신 정보에 근거한 제 생각입니다.

+0

당신은 명확하게이 질문이 무엇인지 묻지 않고 문제의 기능에 익숙하지 않거나 일반적인 기술과 정확히 같은 양의 메모리를 사용한다는 것이 명백합니다. alloc in cocoa, 또는 당신은 내가 바보라고 생각하고 스스로 이것을 깨닫지 못합니다. –

관련 문제