为什么Swift不能自动将泛型类型参数转换为超类?

时间:2018-06-14 13:44:58

标签: swift generics

在Swift中考虑以下内容:

struct GenericStruct<T> {}
class A {}
class B: A {}

func doSomething() -> GenericStruct<A> {
   return GenericStruct<B>()
}

这给出了错误:

  

无法将GenericStruct<B>类型的返回表达式转换为返回类型GenericStruct<A>

BA的子类。

  • 为什么不能将GenericStruct<B>转换为GenericStruct<A>
  • 在这种情况下应该做些什么?

2 个答案:

答案 0 :(得分:8)

Swift泛型是不变的,这意味着两个泛型类型是无关的,即使它们的泛型类型参数具有继承关系。不变的泛型类型不能彼此强制转换,因为它们之间没有任何继承关系。

这意味着GenericStruct<B>GenericStruct<A>完全无关,即使BA的子类,因此您无法将其转换为另一个。

答案 1 :(得分:8)

以下是一个反例,说明如果允许这样做会发生什么:

struct GenericStruct<T> {
    let value: T
}

class A {}
class B: A {}
class C: A {}

let wrapperOfB: GenericStruct<B> = GenericStruct(value: B())
let wrapperOfA: GenericStruct<A> = wrapperOfB // Suppose GenericStruct<B> was a subtype of GenericStruct<A>
wrapperOfA.value = C() // C is an A, so this should be legal

useB(wrapperOfB.value) // Now what?