2016-04-23 1 views
2

У меня есть ряд структур, которые реализуют протокол Resource. Это определяет, что они должны иметь переменную extendedInfo, которая соответствует протоколу ExtendedInfo, чтобы предоставить возможность инициализировать их с помощью json через init(json: [String: AnyObject]. Я пытаюсь предоставить способ динамически создавать их с помощью JSON, предоставляя нужный тип ExtendedInfo и назначая его переменной struct extendedInfo. Тем не менее, я получаю ошибку Argument labels '(json:)' do not match any available overloads при попытке их экземпляры через их dynamicTypeБыстрая инициализация динамического типа с динамическим типом протокола

protocol Resource { 

    associatedtype ExtendedInfoTypeAlias: ExtendedInfo 

    var extendedInfo: ExtendedInfoTypeAlias? { get set } 
} 

protocol ExtendedInfo { 
    init(json: [String: AnyObject]) 
} 

struct User: Resource { 

    typealias ExtendedInfoTypeAlias = UserExtendedInfo 

    let name: String = "Name" 
    var extendedInfo: UserExtendedInfo? 
} 

struct UserExtendedInfo: ExtendedInfo { 

    let age: Int? 

    init(json: [String: AnyObject]) { 
     age = json["age"] as? Int 
    } 
} 


let user = User() 
let sampleJSON = ["age": 50] 

let userExtendedInfo = user.extendedInfo.dynamicType.init(json: sampleJSON) // Argument labels '(json:)' do not match any available overloads 
user.extendedInfo = userExtendedInfo 

Любые идеи, ребята? Благодаря

ответ

1

Прежде всего, вам не нужно явно определить тип ExtendedInfoTypeAlias в вашей реализации структуры - вы можете просто позволить этому быть выведенным по типу, который вы предоставляете для extendedInfo.

struct User: Resource { 
    let name: String = "Name" 
    var extendedInfo: UserExtendedInfo? 
} 

Во-вторых, вы можете просто использовать соответствующий тип в Протоколе ваш дается структура-х dynamicType для того, чтобы использовать свой заданный Инициализатора. Например:

user.extendedInfo = user.dynamicType.ExtendedInfoTypeAlias.init(json: sampleJSON) 
print(user.extendedInfo) // Optional(Dynamic_Protocols.UserExtendedInfo(age: Optional(50))) 

А почему ваш текущий код не работает, я подозреваю, что это связанно с тем, что вы получаете dynamicType от опционального - что мешает вам звонит Инициализатор на него.


Я считаю, что следующие работы, даже когда extendedInfo является nil. (This is a bug).

user.extendedInfo = user.extendedInfo!.dynamicType.init(json: sampleJSON)

+0

Удивительный. Спасибо чувак! – trundrumbalind

+0

@trundrumbalind С удовольствием помогите :) – Hamish

-1

Изменение:

let user = User() 

To:

var user = User() 

и попробовать это:

user.extendedInfo = UserExtendedInfo(json: sampleJSON) 
+0

Идея заключается в том, что я явно не сказать, '... объект ExtendedInfo' Я хочу инициализацию. Я хочу иметь возможность сделать вывод о том, какой из них относится к типу переменной 'extendedInfo', чтобы он мог работать с любым объектом, который придерживается протокола« Ресурс ». – trundrumbalind