您好,我正试图了解Scala。
我指的是API并发现了不熟悉的语法
http://www.scala-lang.org/api/current/#scala.actors.CanReply
trait CanReply[-T, +R] extends AnyRef
abstract type Future[+P] <: () ⇒ P
这个+和 - 在T和R之前意味着什么?
答案 0 :(得分:2)
它们表示协方差和逆变,请参阅http://debasishg.blogspot.ch/2006/04/generics-in-scala-part-1_12.html
具体来说,引用:
类定义的+ in type参数表示 子类型对该类型参数是协变的。 A - 在同一个地方 将关系改为逆变。默认(没有任何 prefix)声明表示子类型的不变性。
答案 1 :(得分:2)
一个简短的(而不是完整的)答案,但没有详细说明:
它们指定类型参数和继承关系之间的关系。
+
表示如果T
是S
的子类,则Class[T]
是Class[S]
的子类-
表示如果S
是T
的子类,则Class[T]
是Class[S]
的子类Class t
和Class s
如果您熟悉Java,那么您知道第三种情况是每个带有类型参数的Java类。 (List<T>
和List<S>
之间没有任何关系,即使T
是S
的子类
答案 2 :(得分:2)
我同意这里的答案,只想展示一些例子。使用[-T, +R]
共同和反差异,您可以执行以下操作:
class A
class B extends A
class C extends B
trait CanReply[-T, +R] {
def foo(r: T): R
}
class CR1 extends CanReply[B, B] {
def foo(r: B): B = {
println("arg of type [" + r.getClass() + "] for B in CR1")
new B
}
}
class CR2 extends CanReply[A, C] {
def foo(r: A): C = {
println("arg of type [" + r.getClass() + "] for A in CR2")
new C
}
}
class CR3 extends CanReply[C, A] {
def foo(r: C): A = {
println("arg of type [" + r.getClass() + "] for C in CR3")
new A
}
}
object Program {
def main(args: Array[String]): Unit = {
test(new CR1)
test(new CR2)
test(new CR3)
}
def test(cr: CanReply[C, A]): Unit = {
val res: A = cr.foo(new C)
println("result of type [" + res.getClass() + "]")
println()
}
}
将产生:
arg of type [class C] for B in CR1
result of type [class B]
arg of type [class C] for A in CR2
result of type [class C]
arg of type [class C] for C in CR3
result of type [class A]
因此,对于反差异,您可以将任何基类对象放置在期望派生的位置,反之亦然,可以将任何派生类对象放在需要基数的位置。通常,方法参数是反变量的,它们的返回类型是共变量。