프로토콜이 특정 클래스에서만 채택되도록 요구하는 방법


91

이 프로토콜을 원합니다.

protocol AddsMoreCommands {
     /* ... */
}

클래스에서 상속 된 클래스에서만 채택됩니다 UIViewController. 이 페이지 는 작성하여 (구조체가 아닌) 클래스에서만 채택되도록 지정할 수 있음을 알려줍니다.

protocol AddsMoreCommands: class {
}

하지만 특정 클래스에서만 채택하도록 요구하는 방법을 알 수 없습니다. 이 페이지는 나중에where 적합성을 확인하기 위해 프로토콜 확장에 절을 추가 하는 방법에 대해 설명하지만 그 방법도 볼 수 없습니다.

extension AddsMoreCommands where /* what */ {
}

이를 수행하는 방법이 있습니까? 감사!

답변:


115
protocol AddsMoreCommands: class {
    // Code
}

extension AddsMoreCommands where Self: UIViewController {
    // Code
}

4
그래서 거의가 ... 내가 쓴했다 self대신 Self벌금을 작동하는, :-( 대단히 감사합니다!
emrys57

나에게 이것은 캐스팅과 함께 사용할 때 약간의 구문 상 이상 함을 유발합니다.
Chris Prince

3
확장은 저장된 속성을 포함 할 수 없기 때문에 프로토콜에 속성을 포함해야하는 경우에는 작동하지 않습니다.
shim

1
다음을 사용하기 만하면됩니다. objc_getAssociatedObject (self, & KeyName) as? PropertyType
Michał Ziobro

이것은 또한하자의 / var 선언이 유형이 때 캐스팅이 필요 AddsMoreCommands하지만 방법은 당신이 예상하는에 패스UIViewController
GoatInTheMachine

80

이는 확장 없이도 가능합니다.

protocol AddsMoreCommands: class where Self: UIViewController {
   // code
}

2017/11/04 편집 : Zig가 지적했듯이 이것은 Xcode 9.1에서 경고를 생성하는 것 같습니다. 현재 Swift 프로젝트 (SR-6265) 에서 경고를 제거하기 위해 보고 된 문제 가 있습니다. 계속해서 주시하고 그에 따라 답변을 업데이트하겠습니다.

EDITED 2018/09/29 : class인스턴스를 저장할 변수가 약해야하는 경우 (예 : 델리게이트) 필요합니다. 약한 변수가 필요하지 않은 경우를 생략 class하고 다음을 작성하면 경고가 표시되지 않습니다.

protocol AddsMoreCommands where Self: UIViewController {
   // code
}

5
내가 2 년 된 질문을 클릭하고 한 시간 전에 게시 된 완벽한 솔루션을 찾은 것은
얼마나 우연한

Xcode 9.1은 이제 Redundant layout constraint 'Self': 'AnyObject'에 대한 경고를 표시합니다. 레이아웃 제약 제약 'Self': 여기에 'AnyObject'가 함축되어 있습니다. 내 코드를 허용되는 답변의 형식으로 변경하는 것이 더 좋은 것 같습니다.
Zig

2
엑스 코드의 9.1 클래스 전용 프로토콜은 현재 사용하는 AnyObject대신 class. protocol AddsMoreCommands: AnyObject where Self: UIViewController { // code }
dodgio

@dodgio 여전히 사용하여 동일한 경고를 받고 있습니다AnyObject
rgkobashi

1
@ DávidPásztor 당신이 맞습니다. 그러나 위임과 같은 구조적 패턴에 그것을 사용하고 싶다면, 속성을 약하게 만들려면 명시 적으로 ´class´를 추가해야합니다. :)
rgkobashi

48

이전 답변의 문제로 인해 다음 선언으로 끝났습니다.

protocol AddsMoreCommands where Self : UIViewController { 
    // protocol stuff here  
}

Xcode 9.1에서 경고 없음


5
내가 틀렸다면 정정하십시오. 그러나 위의 솔루션 (Xcode 9.1 이상에서 경고를 생성 함)에 대한 문제는 위임을 약한 것으로 선언 할 수 없다는 것입니까?
Kyle Goslan 2018

내가 스위프트 4.1이 솔루션을 사용하는 경우 또한, 나는의 주조 특성을 필요 AddsMoreCommandsUIViewController...하는 내가 피하기 위해 원
fl034

9
유형 캐스트를 피하기 위해 다음과 같이 할 수 있습니다.typealias AddsMoreCommandsViewController = UIViewController & AddsMoreCommands
plu

35

이제 Swift 5에서 다음을 수행 할 수 있습니다.

protocol AddsMoreCommands: UIViewController {
     /* ... */
}

아주 편리합니다.

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