Ios 无法推断泛型参数-数组扩展名

Ios 无法推断泛型参数-数组扩展名,ios,swift,Ios,Swift,我有一个通用方法来创建对象,该对象从响应扩展协议 extension FromResponse { static func object<T>(_ response: [String: Any]?) -> T? where T: FromResponse, T: NSObject { guard let response = response else { return nil } let obj: T = T() ret

我有一个通用方法来创建对象,该对象从响应扩展协议

extension FromResponse {
    static func object<T>(_ response: [String: Any]?) -> T? where T: FromResponse, T: NSObject {
        guard let response = response else { return nil }
        let obj: T = T()
        return obj
    }
}
工作做得很好。但有时我会从响应中获取对象数组,因此我也希望使用通用解析器:

static func objects<T>(_ response: [[String: Any]]?) -> [T]? where T: FromResponse, T: NSObject {
    guard let response = response else { return nil }
    var returnArray: [T] = [T]()
    for singleResponse in response {
        if let object: T = T.object(singleResponse) {
            returnArray.append(object)
        }
    }
    return returnArray
}
它说:

无法推断泛型参数“T”

我知道这是什么意思,但我指定了类型,所以这个错误不应该发生。当我这样做时:

var typ: [MyObject] = [MyObject]()
for singleResponse in (response as? [[String: Any]])! {
    let pack: MyObject? = MyObject.object(singleResponse)
    typ.append(pack!)
 }
它起作用了


为什么??如何让解析器返回泛型对象数组?

我不知道为什么斯威夫特说“无法推断泛型参数‘t’”,但我猜这与数组协方差有关

协方差是什么?考虑这一点:

class Base { }
class Sub: Base { }
func f(_ array: [Base]) { }
能否将
[Sub]
传递给
f
?在斯威夫特,你可以。因为
Sub
Base
的子类型,
[Sub]
[Base]
的子类型。(这称为“协方差”),因此您可以将
[Sub]
传递到允许
[Base]
的任何位置:

f([Sub]())
// No errors.
您可以返回一个
[Sub]
,其中需要一个
[Base]

func g() -> [Base] { return [Sub]() }
// No errors.
您可以将
[Sub]
分配给
[Base]
变量:

let bases: [Base] = [Sub]()
// No errors.
回到你的代码:

static func objects<T>(_ response: [[String: Any]]?) -> [T]? ...

let myObjects: [MyObject]? = MyObject.objects(response)
不清楚为什么这个方法在
MyObject
类上。也许您应该将其作为
[[String:Any]]
上的一个方法:

extension Collection where Element == [String: Any] { 
    func objects<T>(ofType type: T.Type) -> [T]? ...
} 

let myObjects = response.objects(ofType: MyObject.self)
扩展集合,其中元素==[String:Any]{
func对象(类型:T.type)->[T]。。。
} 
让myObjects=response.objects(类型:MyObject.self)

我不知道为什么斯威夫特说“无法推断通用参数‘t’”,但我猜它与数组协方差有关

协方差是什么?考虑这一点:

class Base { }
class Sub: Base { }
func f(_ array: [Base]) { }
能否将
[Sub]
传递给
f
?在斯威夫特,你可以。因为
Sub
Base
的子类型,
[Sub]
[Base]
的子类型。(这称为“协方差”),因此您可以将
[Sub]
传递到允许
[Base]
的任何位置:

f([Sub]())
// No errors.
您可以返回一个
[Sub]
,其中需要一个
[Base]

func g() -> [Base] { return [Sub]() }
// No errors.
您可以将
[Sub]
分配给
[Base]
变量:

let bases: [Base] = [Sub]()
// No errors.
回到你的代码:

static func objects<T>(_ response: [[String: Any]]?) -> [T]? ...

let myObjects: [MyObject]? = MyObject.objects(response)
不清楚为什么这个方法在
MyObject
类上。也许您应该将其作为
[[String:Any]]
上的一个方法:

extension Collection where Element == [String: Any] { 
    func objects<T>(ofType type: T.Type) -> [T]? ...
} 

let myObjects = response.objects(ofType: MyObject.self)
扩展集合,其中元素==[String:Any]{
func对象(类型:T.type)->[T]。。。
} 
让myObjects=response.objects(类型:MyObject.self)

您能否向我们展示
MyObject
的声明(以及作为参数传递的
响应
)?我无法重现你的问题。尽管通过让方法分别返回
Self?
[Self]?
可以完全避免这种类型推断的需要(如果需要,可以使用
where Self:NSObject
约束扩展)。你甚至可能想考虑制作<代码>对象(“:”)< /Cord>初始化器。原来这是一个XCODE奇怪的行为,在退出和清除DD后编译…感谢您的评论,您无法重现问题。这就是我要做的。你能给我们看一下
MyObject
的声明(以及作为参数传递的
响应
)吗?我无法重现你的问题。尽管通过让方法分别返回
Self?
[Self]?
可以完全避免这种类型推断的需要(如果需要,可以使用
where Self:NSObject
约束扩展)。你甚至可能想考虑制作<代码>对象(“:”)< /Cord>初始化器。原来这是一个XCODE奇怪的行为,在退出和清除DD后编译…感谢您的评论,您无法重现问题。这让我这么做