예제 - swift4 delay




'순수한'스위프트(@objc없이)에서 약한 프로토콜 참조를 만드는 방법은 무엇입니까? (4)

보충 답변

나는 대의원이 약할 지 여부에 대해 항상 혼란스러워했다. 최근에 대표자와 약한 참조를 더 많이 사용 했으므로 향후 시청자를 위해 보완 요점을 추가하겠습니다.

  • weak 키워드를 사용하는 목적은 강력한 참조주기 (주기 유지)를 피하는 것입니다. 두 개의 클래스 인스턴스가 서로에 대해 강력한 참조를 갖는 경우 강력한 참조주기가 발생합니다. 그들의 참조 카운트는 절대로 0이되지 않으므로 결코 할당이 해제되지 않습니다.

  • 델리게이트가 클래스 인 경우 weak 만 사용해야합니다. Swift 구조체와 열거 형은 참조 유형이 아닌 값 유형 (값이 새 인스턴스가 만들어 질 때 복사 됨)이므로 강력한 참조 주기를 만들지 않습니다.

  • weak 참조는 항상 선택 사항입니다 (그렇지 않으면 unowned 사용됨). 할당 해제 될 때 선택 사항을 nil 로 설정할 수 있도록 항상 var (not let )을 사용합니다.

  • 부모 클래스는 자연스럽게 자식 클래스에 대한 강력한 참조를 가져야하며 weak 키워드를 사용하지 않아야합니다. 아이가 부모에 대한 참조를 원하면 weak 키워드를 사용하여 약한 참조가되어야합니다.

  • weak 은 부모를 참조하는 자식뿐만 아니라 소유하지 않은 클래스에 대한 참조를 원할 때 사용해야합니다. 두 개의 비 계층 적 클래스가 서로를 참조 할 필요가있을 때 하나를 약하게 선택하십시오. 당신이 선택한 것은 상황에 달려 있습니다. 자세한 내용은 이 질문에 대한 답변을 참조하십시오.

  • 일반적으로 대리인은 대부분의 대리인이 소유하지 않은 클래스를 참조하기 때문에 weak 것으로 표시되어야합니다 . 이것은, 아이가 부모와 통신하기 위해서 delegate를 사용하고있는 경우에 확실히 진실입니다. 그러나 대리인이 강력한 참조를 사용하고 사용해야하는 상황 이 여전히 있습니다.

  • 프로토콜은 참조 형식 (클래스)과 값 형식 (구조체, 열거 형) 모두에 사용할 수 있습니다. 따라서 대리인을 약하게 만들 필요가있는 경우 class 키워드를 프로토콜에 추가하여 참조 유형에만 사용해야한다는 것을 알 수 있도록해야합니다.

    protocol MyClassDelegate: class {
        // ...
    }
    
    class SomeClass {
        weak var delegate: MyClassDelegate?
    }
    

더 많은 연구

다음 기사를 읽으면이 점을 훨씬 잘 이해할 수있었습니다. 또한 unowned 키워드 및 폐쇄와 관련된 강력한 참조주기와 같은 관련 문제에 대해서도 논의합니다.

관련

protocol@objc 로 선언되지 않으면 weak 참조가 Swift에서 작동하지 않는 것처럼 보입니다.이 protocol 은 순수 Swift 앱에서 필요하지 않습니다.

이 코드는 컴파일 오류를 발생시킵니다 (비 weak 클래스 MyClassDelegate weak 을 적용 할 수 없음).

class MyClass {
  weak var delegate: MyClassDelegate?
}

protocol MyClassDelegate {
}

나는 프로토콜에 @objc 접두사를 @objc .

질문 : weak delegate 을 수행하는 '순수한'신속한 방법은 무엇입니까?


Apple은 "클래스"대신 "NSObjectProtocol"을 사용합니다.

public protocol UIScrollViewDelegate : NSObjectProtocol {
   ...
}

이것은 또한 나를 위해 작동하고 내 자신의 대리자 패턴을 구현하려고 할 때보고 있던 오류를 제거했습니다.


AnyObject 는 Swift에서 약한 참조를 사용하는 공식적인 방법입니다.

class MyClass {
    weak var delegate: MyClassDelegate?
}

protocol MyClassDelegate: AnyObject {
}

Apple의 경우 :

강력한 참조주기를 방지하려면 대리자를 약한 참조로 선언해야합니다. 약한 참조에 대한 자세한 내용은 클래스 인스턴스 간 강력한 참조주기를 참조하십시오. 프로토콜을 클래스 전용으로 표시하면 나중에 대리인이 약한 참조를 사용해야한다고 선언 할 수 있습니다. Class-Only Protocols에서 논의 된 것처럼 AnyObject 를 상속하여 프로토콜을 클래스 전용으로 표시합니다.

https://developer.apple.com/library/content/documentation/Swift/Conceptual/Swift_Programming_Language/Protocols.html#//apple_ref/doc/uid/TP40014097-CH25-ID276


업데이트 : 매뉴얼이 업데이트되었고 내가 언급 한 예가 삭제 된 것처럼 보입니다. 위의 @ flainez의 대답을 편집하십시오.

원본 : Obj-C와 상호 운용하지 않는 경우에도 @objc를 사용하는 것이 올바른 방법입니다. 그것은 프로토콜이 enum이나 struct가 아닌 클래스에 적용되도록합니다. 설명서의 "프로토콜 적합성 검사"를 참조하십시오.





swift-protocols