본문 바로가기

[Swift 5.1] 키 패스를 이용한 동적 멤버 찾아보기 (SE-0252)

기술적인 이야기/애플 플랫폼 개발 2019. 10. 30.
반응형

이 글은 SE-0252 Key Path Member Lookup 제안을 통해 Swift 5.1에서 확장된 동적 멤버 찾아보기(dynamic member lookup) 기능을 간략히 살펴보는 글입니다.

이 업데이트는 Swift 4.2에서 추가된 @dynamicMemberLookup의 기능을 좀 더 확장시킵니다. 일단 다짜고짜 기존(?) 예제부터 봅시다.

@dynamicMemberLookup
struct SomeInfo {
    let properties: [String : String] = [
        "name": "James",
        "city": "LA"
    ]

    subscript(dynamicMember string: String) -> String {
        return properties[string]!
    }
}

let info = SomeInfo()
info.name   // "James"
info.city   // "LA"

첫 줄의 @dynamicMemberLookup이 이번 글의 핵심 키워드입니다. 그리고 이를 구현하는 부분이 subscript 부분입니다. subscript(dynamicMember:)를 통해 사전형 프로퍼티에 액세스를 하고 있는데 문자열이 아니라 마치 일반 프로퍼티처럼 액세스 할 수 있게 만들어 주는 것이 바로 이 Dynamic Memeber Lookup의 기능입니다.

다만 이 예제는 5.1 업데이트 내용을 설명하기에는 좀 부족함이 있습니다.

5.1에서 확장된 기능에 맞게 다른 예제를 살펴봅시다.

@dynamicMemberLookup
struct Humanlike<T> {
    private let primate: T

    init(_ p: T) {
        primate = p
    }

    subscript<U>(dynamicMember keyPath: WritableKeyPath<T, U>) -> U {
        return primate[keyPath: keyPath]
    }
}

이름은 인류(Humanlike)라는 거창한 이름인데 subscript를 빼면 별로 하는 일이 없는 코드네요. 근데 subscript 부분에 KeyPath를 사용하고 있다는 점이 좀 달라 보입니다. 어쨌든 이 구조체는 아마도 단독으로 사용하기 위한 용도는 아닐 거라고 생각되실 겁니다. 이제 다른 인스턴스를 넣어서 테스트해 봅시다.

struct HomoSapiens {
    var name: String = "James"
    var age: Int = 38
}

let a = Humanlike(HomoSapiens())
a.name      // "James"
a.age       // 38

호모사피엔스(HomoSapiens) 구조체를 하나 선언하고 인스턴스를 생성한 후 이를 Humanlike 구조체를 통해 액세스 하는 예제입니다. 여기서 Humanlike 구조체는 마치 자신의 프로퍼티인 것처럼 HomoSapiens 타입 인스턴스의 프로퍼티인 nameage에 액세스 할 수 있게 해주고 있습니다.

하나 더 시험해 볼까요?

struct Ramapithecus {
    var age: Int = 2
    var skinRate: Float = 0.2
}

let b = Humanlike(Ramapithecus())
b.age       // 2
b.skinRate  // 0.2
b.name      // error: value of type 'Ramapithecus' has no member 'name'

라마피테쿠스(Ramapithecus) 구조체를 하나 더 만들고 역시 이것의 인스턴스를 Humanlike를 통해 액세스 하는 예제입니다. 다만 이번에는 Ramapithecus에는 없는 프로퍼티를 액세스 하려 하였고 당연하게도 에러가 나고 있는 모습을 볼 수 있습니다. 그리고 그 에러 또한 아주 명백하게 Ramapithecus 인스턴스를 액세스 하려다 에러가 난 것처럼 보이기도 하네요.

대충 이런 식으로 쓰려고 만들어진 것이 이 @dynamicMemberLookup입니다. 앞의 예제에서 봤다시피 이번 5.1에서는 문자열 기반에서 탈피하여 키 패스(Key Path)를 활용해서 사용할 수 있게 되어서 좀 더 쓸모 있게 변화 되었다는 것이 핵심입니다.

728x90
반응형

댓글