-retainCount를 언제 사용합니까?


110

-retainCount지금까지 어떤 상황에서 사용 하셨는지 , 그리고 결국 사용할 때 발생할 수있는 문제 를 알고 싶습니다 .

감사.


5
당신이해야 결코 사용자 -retainCount.
holex

3
(필요한 경우를 제외하고. 때때로 심각하게 오해의 소지가있을 수 있다는 점을 이해하는 한 진행 상황을 이해하는 데 도움이되는 경우가 있습니다. 물론 ARC를 사용하는 경우에는 전혀 허용되지 않습니다.)
Hot Licks

답변:


243

-retainCount유용한 정보를 알려주지 않기 때문에 절대 사용해서는 안됩니다 . Foundation 및 AppKit / UIKit 프레임 워크의 구현은 불투명합니다. 무엇을 보유하고 있는지, 왜 보유하고 있는지, 누가 보유하고 있는지, 언제 보유하고 있는지 등을 알 수 없습니다.

예를 들면 :

  • 1의 값을 [NSNumber numberWithInt:1]가질 것이라고 생각할 것입니다 retainCount. 그렇지 않습니다. 2입니다.
  • 1의 값을 @"Foo"가질 것이라고 생각할 것입니다 retainCount. 그렇지 않습니다. 1152921504606846975입니다.
  • 1의 값을 [NSString stringWithString:@"Foo"]가질 것이라고 생각할 것입니다 retainCount. 그렇지 않습니다. 다시 1152921504606846975입니다.

기본적으로 어떤 것이 든 객체를 유지할 수 있고 (따라서 해당를 변경할 수 있으며 retainCount) 응용 프로그램을 실행하는 대부분의 코드에 대한 소스가 없기 때문에 객체의 retainCount의미가 없습니다.

객체가 할당 해제되지 않는 이유를 추적하려면 Instruments의 Leaks 도구를 사용하십시오. 개체가 너무 빨리 할당 해제 된 이유를 추적하려면 Instruments의 Zombies 도구를 사용하십시오.

그러나 -retainCount. 정말 쓸모없는 방법입니다.

편집하다

모두 http://bugreport.apple.com으로 이동하여 -retainCount더 이상 사용되지 않도록 요청하십시오 . 요청하는 사람이 많을수록 좋습니다.

편집 # 2

업데이트로 [NSNumber numberWithInt:1]이제는 retainCount9223372036854775807입니다. 코드에서 2가 될 것으로 예상했다면 이제 코드가 손상되었습니다.


4
예를 들어 @ Dave-Delong에게 감사드립니다.
Moszi 2011 년

1
preserveCount는 현재 싱글 톤에 유용합니다. (이제 질문은 싱글 톤이 얼마나 유용한 지입니다 ...) - (NSUInteger)retainCount{return NSUIntegerMax;}.

8
@Joe 재정의하지 않고 싱글 톤을 만들 수 있습니다 retainCount.
Dave DeLong 2011 년

5
@Joe 나는 그것을 알고있다; 이 예제가 그다지 좋은 예제가 아닌 이유에 대한 모든 토론에 대한 Google "objective-c singleton".
Dave DeLong 2011 년

2
내가 사용하는 한 가지-@ DaveDeLong, 당신도이 문제를 발견 할 수 있지만 그렇게 생각하지 않는다-는 deallocs와 inits를 덮어 쓰고 NSLogs를 넣는 것입니다. 이 .. 나에게 우리가 일반적으로 대답하기 위해 노력하고 실제 문제는 객체가 dealloced 여부지고 있는지 여부의 좋은 아이디어를 제공합니다
댄 Rosenstark는에게

50

못!

진지하게. 그냥 하지마.

그냥 따라 메모리 관리 지침을 하고 만 것을 해제 alloc, new또는 copy(또는 아무것도 당신이라는 retain원래시).

@bbum은 여기에서 최고라고 말했고 그의 블로그 에서 더 자세히 설명했습니다 .


8
기억을 세고 있다고 생각하지만 잘못하고있을 것이기 때문입니다.
Abizern 2011 년

@ Abizern-그리고 다른 답변 중 하나에서 싱글 톤 상황은 어떻습니까?
Moszi 2011 년

3
여기에 추가하기 위해, 얻을 -retainCount수있는 모든 정보 는 Instruments 및 도구에서 얻을 수 있습니다 (훨씬 더 자세히).
Dave DeLong 2011 년

3
Dave가 말한 것을 추가하려면; 객체의 절대 보유 수는 구현 세부 사항입니다. 개체 내부의 세부 정보 및 / 또는 개체가 통과했을 수있는 다른 개체의 세부 정보입니다. 호출 retain, retain, retain, autorelease, 오토 릴리즈, autorelease예를 들어, UIKit API를 통해 객체를 전달하는 완벽하게 유효한 결과 일 수있다.
bbum 2011 년

2
@ d11wtq preserveCount ever == 0이면 특이점이 달성 된 것입니다!
bbum 2011 년

14

Autoreleased 개체는 -retainCount 확인이 정보가없고 잠재적으로 오해의 소지가있는 경우입니다. 보유 수는 객체에서 -autorelease가 호출 된 횟수와 현재 autorelease 풀이 소모 될 때 해제 될 시간에 대한 정보가 없습니다.


1
감사합니다. 이것은 좋은 지적입니다. 이것은 일반적인 "안함"외에 retainCount를 사용하지 않는 이유를 실제로 설명하는 첫 번째 답변입니다.
Moszi 2011 년

1
@Moszi : 귀하의 질문은 "retainCount를 언제 사용해야합니까?"였습니다. — 그 질문을 할 생각이 아니라면 다른 질문을 했어야합니다.
Chuck

@chuck-사실 저는 "언제 사용할지"에 관심이 있었지만 모든 대답은 "절대"가 아닐 것 같습니다 ...하지만-당신이 옳다고 생각합니다. 나는 이틀 동안 질문을 열어두고, 다른 대답이 없을 거라면 절대로 "절대"를 대답으로 받아 들일 것입니다.
Moszi 2011 년

10

내가 '악기'를 사용하여 확인할 때 매우 유용 retainCounts을 찾을 수 있습니다.

'allocations'도구를 사용하여 'Record reference counts'가 켜져 있는지 확인하고 모든 개체로 이동하여 retainCount 기록을 볼 수 있습니다.

할당과 해제를 페어링하면 진행 상황에 대한 좋은 그림을 얻을 수 있으며 종종 무언가가 해제되지 않는 어려운 경우를 해결할 수 있습니다.

이것은 iOS의 초기 베타 릴리스에서 버그를 찾는 것을 포함하여 결코 실망시키지 않았습니다.


5

NSObject에 대한 Apple 문서를 살펴보면 다음과 같은 질문을 거의 다룹니다. NSObject preserveCount

간단히 말해, 자신의 참조 계수 시스템을 구현하지 않는 한 preserveCount는 아마도 쓸모가 없을 것입니다 (그리고 거의 없을 것이라고 보장 할 수 있습니다).

Apple의 말에 따르면, preserveCount는 "일반적으로 메모리 관리 문제를 디버깅 할 때 가치가 없습니다".


우선 답변 해 주셔서 감사합니다. 일반적으로이 질문에 대한 사람들의 반응은 "절대"입니다. (답변 참조). 실제로 "디버깅에 가치 없음"은 "절대"를 의미하지 않습니다. 그래서 제 질문은 – 왜 그것을 사용하지 않는다는 강한 느낌이 들까 요 (예를 들어 싱글 톤 구현에서 – 다시 대답 중 하나)?
Moszi 2011 년

나는 당신이 그것을 사용하는 것에 대한 더 많은 정보를 제공해야 할 것 같습니다. 허용 가능한 사용은 Apple에서 제안한대로 preserveCount를 재정 의하여 자체 참조 계수 시스템을 구현하는 것입니다. 그러나 실제로는 결코 보지 못할 것입니다 (어쨌든 나는 결코 가지고 있지 않습니다). 강력한 반응은 일반적으로 Apple이 자신의 메일 그룹, 문서, 개발자 포럼 등에서 preserveCount를 그대로 두도록 옹호 한 사실에서 비롯됩니다.
lxt 2011 년

1
@Moszi : 디버깅은 대부분의 사람들이 가치가 있다고 생각할 수있는 유일한 상황이므로 신뢰할 수없는 경우 유용하지 않습니다. 다른 용도로 생각하고 있습니까?
Chuck 2011 년

4

물론 값의 의미는 객체에 적용된 autoreleases 수에 따라 다르며 예측할 수없는 것이기 때문에 코드에서 preserveCount 메서드를 사용해서는 안됩니다. 그러나 디버깅에는 매우 유용합니다. 특히 메인 이벤트 루프 외부에서 Appkit 개체의 메서드를 호출하는 코드에서 메모리 누수를 찾을 때 유용하며 더 이상 사용되지 않아야합니다.

당신의 요점을 밝히기 위해 당신은 가치의 불가해 한 특성을 심각하게 과장했습니다. 항상 참조 횟수가 아니라는 것은 사실입니다. 플래그에 사용되는 몇 가지 특수 값이 있습니다. 예를 들어 객체가 할당 해제되지 않아야 함을 나타냅니다. 1152921504606846975와 같은 숫자는 16 진수로 작성하고 0xfffffffffffffff를 얻을 때까지 매우 신비 해 보입니다. 그리고 9223372036854775807은 16 진수로 0x7fffffffffffffff입니다. 그리고 누군가가 이와 같은 값을 플래그로 사용하기로 선택하는 것은 그리 놀라운 일이 아닙니다 .RetainCount를 초당 100,000,000 번 증가 시켰다고 가정 할 때 retainCount를 더 큰 숫자만큼 높이는 데 거의 3000 년이 걸리기 때문입니다.


3

그것을 사용함으로써 어떤 문제를 얻을 수 있습니까? 그것이하는 일은 객체의 보유 수를 반환하는 것뿐입니다. 나는 그것을 한 번도 부르지 않았고 내가 할 이유를 생각할 수 없습니다. 그래도 할당이 해제되지 않도록 싱글 톤으로 재정의했습니다.


2
싱글 톤의 경우이를 재정의 할 이유가 없습니다. Foundation / CoreFoundation retainCount에는 메모리 관리에 사용하는 코드 경로가 없습니다 .
bbum 2011 년

릴리스가 dealloc을 호출해야하는지 결정하는 데 사용하지 않습니까?
ughoavgfhw

2
아니; 유지 / 릴리스 / 자동 릴리스의 내부 구현은 CoreFoundation에 깊은 뿌리를두고 있으며 실제로 예상 할 수있는 것과 전혀 다릅니다. CoreFoundation 소스 (사용 가능)를 가져 와서 살펴보십시오.
bbum 2011 년

3

앱이 실행되고 유용한 작업을 수행 할 때까지 메모리 누수에 대해 걱정할 필요가 없습니다.

그렇다면 Instruments를 실행하고 앱을 사용하여 메모리 누수가 실제로 발생하는지 확인하십시오. 대부분의 경우 개체를 직접 생성하고 (따라서 소유하고 있음) 완료 한 후에 해제하는 것을 잊었습니다.

코드를 작성할 때 코드를 최적화하려고 시도하지 마십시오. 실제로 앱을 정상적으로 사용할 때 메모리 누수 나 시간이 너무 오래 걸릴 수 있다는 추측이 잘못된 경우가 많습니다.

예를 들어 alloc 등을 사용하여 객체를 생성하는 경우 올바른 코드를 작성하고 올바르게 해제했는지 확인하십시오.


0

코드에서 절대 사용해서는 안되지만 디버깅 할 때 확실히 도움이 될 수 있습니다.


0

코드에서 -retainCount를 사용하지 마십시오. 그러나 사용하면 0을 반환하지 않습니다. 이유를 생각해보십시오. :-)


0

Dave의 게시물에 사용 된 예제는 NSNumber 및 NSStrings입니다 ... 따라서 UIViews와 같은 다른 클래스를 사용하면 올바른 답을 얻을 수 있습니다 (유지 횟수는 구현에 따라 다르며 예측 가능합니다).

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.