본문 바로가기

스피드 문법정리

20. Protocol

Protocol

 

 

클래스와 구조체 같은 형식들이 프로토콜에 선언되어있는 멤버를 실제로 구현 

반드시 프로토콜에 선언되어있는 필수맴버를 모두 구현해야 함 

 

 

 

 

 

 

 

 

protocol ProtocolName {
    propertyRequirements
    methodRequirements
    initializerRequirements
    subscriptRequirements
}
protocol ProtocolName : Protocol, ... {
}
protocol Something {
    func doSomething()
}

Adopting Protocol

enum TypeName : ProtocolName, ... {
}
struct TypeName : ProtocolName, ... {
}
class TypeName : SuperClass, ProtocolName, ...{
}

메소드를 구현할 때 메서드의 헤드 부분만 일치시켜주면 되고 메서드 바디는 자유롭게 구현 가능

protocol Something {
    func doSomething()
}

struct Size : Something {
    func doSomething()
    }    
}

Class - Only Protocols

클래스에서만 사용가능한 Protocol 

protocol ProtocolName : AnyObject {
}
protocol Something {
    func doSomething()
}

protocol SomethingObject : Anyobject, something {
}

class Object : SomethingObject {
    func doSomething() {
    }
}

Property Requirements

프로토콜에 포함된 var 키워드는 가변성과는 상관이 없음 -> 선언하는 멤버가 속성이라고만 나타냄

get set 키워드가 속성의 가변성을 결정 -> get, set 키워드가 모두 포함되어있다면 형식에서 읽기와 쓰기가 가능한 속성을 선언해야 함

set만 선언된 경우 형식에서 읽기 전용으로 선언해도 되고 읽기 쓰기가 모두 가능한 형식으로 선언 가능

protocol ProtocolName {
    var name : Type { get set }
    static var name : Type { get set }
}
protocol Figure {
    var name : String { get }
}

struct Rectangle : Figure {
    let name = "Rect"
}

struct Triangle : Figure {
    var name = "Triangle"
}

struct Circle : Figure {
    var name : String {
        return "Circle"
    }
}
protocol Figure {
    var name : String { get }
}

struct Rectangle : Figure {
    var name = "Rect"
}

struct Triangle : Figure {
    var name = "Triangle"
}

struct Circle : Figure {
    var name : String {
        return "Circle"
    }
    set {
    }
}

static 키워드로 선언된 속성은 subclass로 상속되지만 overriding은 금지, overriding을 허용하기 위해서는 static 대신 class로 선언해야 함, name 속성은 여전히 형식 속성이고, 이름과 자료형이 동일하고 가변성도 동일 -> 프로토콜의 요구사항을 충족시키고 subclass에서 overriding도 가능

protocol Figure {
    static var name : String { get }
}

struct Rectangle : Figure {
    static var name = "Rect"
}

struct Triangle : Figure {
    static var name = "Triangle"
}

class Circle : Figure {
    class var name : String {
        return "Circle"
    }
    set {
    }
}

Method Requirements

protocol ProtocolName {
    func name(parm) -> ReturnType
    static func name(param) -> ReturnType
    mutating func name(param) -> ReturnType
}
protocol Resettable {
    func reset()
}

class Size : Resettable {
    var width = 0.0
    var height = 0.0
    
    func reset() {
        width = 0.0
        height = 0.0
    }
}

갑 형식의 인스턴스 메서드에서 속성을 바꾸기 위해서는 func 키워드 앞에 mutating 키워드를 추가해야 함

프로토콜은 mutating 키워드에 따라 메서드를 구분 -> 프로토콜에서도 mutating을 추가해야 함

프로토콜에서 mutating으로 선언했다 해서 class에서 채용할 수 없는 것은 아님

protocol Resettable {
    mutating func reset()
}

struct Size : Resettable {
    var width = 0.0
    var height = 0.0
    
    mutating func reset() {
        width = 0.0
        height = 0.0
    }
}

protocol Resettable {
    mutating func reset()
}

class Size : Resettable {
    var width = 0.0
    var height = 0.0
    
    func reset() {
        width = 0.0
        height = 0.0
    }
}

protocol Resettable {
    static func reset()
}

class Size : Resettable {
    var width = 0.0
    var height = 0.0
    
    func reset() {
        width = 0.0
        height = 0.0
    }
    
    class func reset() { // 클래스로 구현할 경우 overriding 허용
    }   
    static func reset() { // static 으로 구현할 경우 overriding 불가
    }
}

Initalizer Requirements

protocol ProtocolName {
    init(param)
    init?(param)
    init!(param)
}

 

 

 

 

 

 

 

 

 

 

 

 

 

 

'스피드 문법정리' 카테고리의 다른 글

10. Closures  (0) 2020.06.26
11. String and Character  (0) 2020.06.24
18. Initializer and Deinitializer  (0) 2020.06.22
17. Inheritance and Polymorphism  (0) 2020.06.19
16. Method and Subscript  (0) 2020.06.19