页: 1 要求打电话者通过<代码>BaseResp<Any>或次类。 这样就可以在类似情况下通过。
class Sample: BaseResp<Any>()
but not
class Sample: BaseResp<String>()
In short, Fee<T>: Foo<T>
works, but Fee<X:T>: Foo<T>
won t.
您将<代码>改为代码>
inline fun <reified T:BaseResp<out Any>> send(cb: IMessageCallback<T>?)
it ll work. Note the out Any
- this is a covariant type parameter (and is called "Type Projection"), and treats a BaseResp<String>
(or any other type in place of String
) as a subtype of BaseResp<Any>
.
Now you can use BaseResp<String>
as well as Sample
.
Note that because we ve defined the type of data
as out
in the declaration of send
, you can only read the data
from the BaseResp
inside send
, you can t write it. This restriction makes it possible to pass in subtypes of that parameter.
(To be a little more general to explain, if your function takes a MutableList<Animal>
, you could read and write any type of Animal
to that list. But you could only pass in exactly a MutableList<Animal>
. If you changed it to MutableList<out Animal>
, we could now pass in a MutableList<Dog>
or MutableList<Cat>
because you re guaranteeing you re only going to read items from that list - Dog
s and Cat
s can be read as Animal
s. But the function has no idea what type is valid to put into that list - all it knows are Animal
s. Because the incoming list could only store Dog
s and Cat
s (and their subtypes), the function using out
can t be allowed to write to it.)
If the data
inside BaseResp
could be a val
, you could use declaration-site variance to define this for all instances of BaseResp
. For example:
open class BaseResp<out T>(val data:T? = null)
因此,你不需要在<代码>末代码>的声明中进行类型的预测(out
),而且你也经常在任何地方使用。 这取决于您是否真正需要<代码><>数据>/代码>,作为<代码>var;对于答复类型而言,你可能使之不可更改。
I d recommend reading Generics: in, out, where in the Kotlin docs for more detail.