iOS5의 강하고 약한 저장소에 대한 설명


114

저는 iOS5 개발이 처음이고 objective-c를 사용합니다. 차이점을 이해하는 데 어려움이 있습니다.저장 용량의 강함약함 있습니다. 문서 및 기타 SO 질문을 읽었지만 더 이상 통찰력이 없으면 모두 동일하게 들립니다.

나는 읽었다 문서를 습니다. Transitioning To ARC -iOS4의 보유, 할당 및 릴리스 약관을 참조합니다. 저를 혼란스럽게합니다. 그런 다음 Open U CS193p를 살펴보고 강점과 약점을 구분합니다.

Strong : "더 이상 가리 키지 않을 때까지 힙에 보관"
보관합니다." 약함 : "다른 사람이 강하게 가리키고있는 한이 항목을 보관합니다."

두 정의가 동일하지 않습니까? = 포인터가 더 이상 객체를 가리 키지 않으면 객체를 보유한 메모리를 해제합니까? 포인터, 힙, 메모리 할당 또는 할당 해제의 개념을 이해합니다. 그러나 강함과 약함의 차이점은 무엇입니까?


ARC를 사용하는 경우에도 메모리 관리 모델은 여전히 ​​관련이 있습니다. 여전히 참조 계산을 이해해야하며 수동으로 수행 할 필요가 없습니다. 따라서 마지막 단락은 불합리한 요구입니다.
jrturton

답변:


509

차이점은 강한 개체가 없으면 바로 개체가 할당 해제된다는 것입니다. 포인터 된다는 것입니다. 약한 포인터가 가리키는 경우에도 마지막 강한 포인터가 사라지면 개체가 할당 해제되고 나머지 약한 포인터는 모두 제로화됩니다.

아마도 예가 순서 일 것입니다.

우리의 물체가 개이고 그 개가 도망 치고 싶어한다고 상상해보십시오 (할당 해제 됨).

강력한 포인터는 강아지의 끈과 같습니다. 개에 목줄이 붙어있는 한 개는 도망 가지 않습니다. 5 명이 한 마리의 개에게 가죽 끈을 붙이면 (한 물체에 5 개의 강한 포인터), 다섯 마리의 가죽 끈이 모두 분리 될 때까지 개는 도망 가지 않습니다.

반면에 약한 포인터는 어린 아이가 개를 가리키며 "봐! 개!"라고 말하는 것과 같습니다. 개가 여전히 목줄에있는 한 어린 아이들은 여전히 ​​개를 볼 수 있으며 여전히 개를 가리킬 것입니다. 그러나 모든 목줄이 분리 되 자마자 얼마나 많은 어린 아이들이 그것을 가리키고 있더라도 개는 도망칩니다.

마지막 강력한 포인터 (끈)가 더 이상 개체를 가리 키지 않으면 해당 개체는 할당 해제되고 모든 약한 포인터는 0이됩니다.


2
이것은 Apple의 Malcom Crawford가 몇 년 전의 비유를 기반으로합니다. 그가 어디서 얻었는지 모르겠어요.
BJ Homer

책에서 비슷한 (사전 아크)을 읽은 기억이 있습니다. Hillegass라고 생각했지만 다른 곳에서 얻을 수 있었을 것입니다 ... 그래도 좋은 것입니다!
jrturton

14
+1 훌륭한 예. 이것은 가죽 끈이 어떻게 유지 / 해제되는지에 대한 Hillegass의 예에서 파생 된 것이지만, 저는 강 / 약함을위한이 적응을 좋아합니다.
Dave DeLong 2012

2
@DaveDeLong : 글쎄, 그들은 ARC와 함께 10.6에서 불법 입니다. 전혀 사용할 수 없습니다. 그래서 그것은 약간 관련이 없습니다.
BJ Homer

5
또 다른 좋은 점은 헬륨 풍선입니다. 적어도 하나의 줄을 잡고있는 한, 그것은 떠내려 가지 않을 것입니다. 목줄 / 풍선 비유는 사람들이 "소유권"이 유지 / 해제에 의해 관리된다는 사실을 잊게하는데도 좋습니다.
Steve Weller 2012

34

두 정의가 동일하지 않습니다.

절대적으로하지. 당신이 지적한 두 정의의 주요 차이점은 "다른 사람만큼 오래"입니다. 중요한 것은 "다른 사람"입니다.

다음을 고려하세요:

__strong id strongObject = <some_object>;
__weak id weakObject = strongObject;

이제 우리는 <some_object>강한 것과 약한 것에 대한 두 개의 포인터를 얻었습니다 . 이렇게 설정 strongObject하면 nil:

strongObject = nil;

그런 다음 요약 한 규칙을 살펴보면 다음과 같은 질문을 할 것입니다.

  1. 강력 함 : "더 이상 가리 키지 않을 때까지 힙에 보관"

    strongObject<some_object>더 이상 가리 키지 않습니다 . 그래서 우리는 그것을 유지할 필요가 없습니다.

  2. 약함 : "다른 사람이 강력하게 지적하는 한 유지"

    weakObject여전히을 가리 킵니다 <some_object>. 그러나 아무도 이후 다른 그것에 점,이 규칙은 우리가 그것을 보관할 필요가없는 것을 의미한다.

그 결과 <some_object>할당이 취소되고 런타임에서 지원하는 경우 (Lion 및 iOS 5 이상) weakObject자동으로로 설정됩니다 nil.

이제 우리는 설정하면 어떻게됩니까 고려 weakObject하기 nil때문에 좋아한다 :

weakObject = nil;

그런 다음 요약 한 규칙을 살펴보면 다음과 같은 질문을 할 것입니다.

  1. 강력 함 : "더 이상 가리 키지 않을 때까지 힙에 보관"

    strongObject을 가리 킵니다 <some_object>. 그래서 우리는 그것을 유지해야합니다.

  2. 약함 : "다른 사람이 강력하게 지적하는 한 유지"

    weakObject가리 키지 않습니다 <some_object>.

그 결과, 즉 <some_object>되어 있지 해제하지만, weakObject될 것 nil포인터.

[가정하는 모든 것은 <some_object>다른 곳의 강력한 참조 / "보유"되는 다른 수단에 의해 지적되지 않습니다.]


1
따라서 강함과 약함의 주요 차이점은 강하게 가리키는 객체의 할당 해제가 관련된 모든 약한 포인터를 자동으로 제거한다는 것입니다. 약한 포인터가 무언가를 가리 키기 위해서는 항상 강한 포인터가 존재합니다. 그렇다면 기본 응용 프로그램 개체를 강력하게 가리켜 야합니까?
KMC

약한 포인터가 유효한 것을 가리 키려면 강력한 포인터가 있어야합니다. 여기에 iOS 5 및 Lion이 약한 참조의 자동 무효화를 지원한다는 사실을 추가하면 말한 내용을 얻을 수 있습니다. 하지만 iOS 4의 런타임은 이를 지원 하지 않습니다 . "주 응용 프로그램 개체"는 UIApplication개체 를 의미한다고 가정 합니까? 그것은 내부 작업에 의해 강력하게 참조 될 것입니다. UIKit그러나 그것에 대해 걱정할 필요가 없습니다.
mattjgalloway

"strongObject"대신 "strongObjectPointer"와 같은 단어를 사용할 수 있다고 생각합니다. 그래서 프로그래밍에 새로운 사람들은 더 나은 의미를 가질 것입니다. :) @BJ 호머 포스트 Mr.Matt.Interesting에 좋은 캐치
Vijay-Apple-Dev.blogspot.com

2

강한

  1. 속성과 할당 된 값 간의 소유권을 생성합니다.
  2. 이것은 ARC의 객체 속성에 대한 기본값이므로 참조 횟수에 대해 걱정하지 않고 참조를 자동으로 해제 할 수 있습니다.
  3. 유지를위한 교체입니다. 우리는 유지로 사용해야하는 경우에만 사용합니다.

약한

  1. 재산과 할당 된 가치 사이에 비 소유권을 생성합니다.
  2. Strong은 부모 개체에 사용되고 weak는 부모가 해제되면 자식 개체에 사용되며 자식 개체 참조도 nil로 설정됩니다.
  3. 유지주기를 방지하는 데 도움이됩니다.
  4. 가비지 수집기에서 수집 할 때 참조 된 개체를 보호하지 않습니다.
  5. 약함은 본질적으로 할당되고 유지되지 않는 재산입니다.

여기에서 일반적으로 유지주기가 무엇인지 언급 할 가치가 있습니다. 객체 A와 객체 B의 두 가지 객체가 있습니다. 객체 A는 객체 B에 대한 강력한 참조를 갖고 객체 B는 객체 A에 대한 강력한 참조를 가지고 있습니다. 다른 어떤 것도 객체 A 또는 B에 대한 강력한 참조를 가지고 있지 않습니다.
boro

2

또 다른 예 : 학생은 선택 과목 ( ) 수강 여부에 관계없이 모든 핵심 과목 ( ) 을 마치면 Object졸업 ( deallocate) 할 수 있다고 가정합니다 . 즉, 강력한 포인터는 할당 해제의 유일한 요소입니다 .strong pointersweak pointersObject


1

아니요, 동일하지는 않지만 매우 다릅니다. 물건을 유지해야하는 경우에만 strong을 사용합니다. 다른 경우에는 weak를 사용하며, 아무도 개체를 보유하고 있지 않기 때문에 개체 ha가 힙에서 제거되었는지 알 수 있다는 이점이 있습니다.


1

나는 내가이 파티에 다소 늦었다는 것을 알고 있지만, "강하고 약한 메모리 모델"의 의미는 소프트웨어 또는 하드웨어에 대해 이야기하고 있는지에 따라 다르다는 점을 지적하여 문제를 혼동하는 것이 중요하다고 생각합니다.

하드웨어의 경우 약함 또는 강함은 순차 일관성을 지원하는지 여부를 나타냅니다.

[SC 의미] ... 모든 프로세서의 작업이 순차적으로 실행 된 것과 동일하며 각 개별 프로세서의 작업은 프로그램에서 지정한 순서대로이 순서로 나타납니다. - 램 포트 1979

WTF가 메모리와 관련이 있습니까? 다른 프로세서에 의한 변수 쓰기는 모든 프로세서에서 동일한 순서로 보여야 함을 의미합니다. 강력한 모델의 하드웨어에서는 이것이 보장됩니다. 약한 모델의 하드웨어에서는 그렇지 않습니다.

기존 답변은 소프트웨어 메모리 모델 측면에서만 질문을 해석합니다. 하드웨어는 프로그래밍과 관련이 없습니다. 이 질문은 일반적으로 Arm7 프로세서에서 실행되는 iOS에 대해 언급합니다. Arm7은 메모리 모델이 약합니다. 강력한 모델을 사용하는 프로세서에 익숙한 프로그래머에게 이것은 x86과 x64가 강력한 모델을 가지고 있기 때문에 우리 모두에게 해당됩니다. 이것은 끔찍한 함정입니다. bool을 사용하여 다른 스레드에 종료 신호를 보내는 것은 강력한 모델에서 잘 작동합니다. Arm의 동일한 코드는 플래그를 volatile로 표시하지 않는 한 전혀 작동하지 않으며 심지어는 비정상적입니다.

Arm8 +가 인수 / 출시에 대한 명시적인 지원으로이를 완전히 변경하는 것은 사실이지만 레거시 소프트웨어는이 지원을 사용하지 않습니다. 레거시 소프트웨어에는 업데이트 될 때까지 컴파일러와 라이브러리뿐만 아니라 세 가지 전화 OS와 여기에서 실행되는 모든 것이 포함됩니다.

이 주제에 대한 확장 된 검토를 위해 나는 당신을 흉내낼 수없는 Herb Sutter를 추천 합니다.

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