gpt4 book ai didi

Scala 2.11.8 类型标签并不总是由编译器正确生成

转载 作者:行者123 更新时间:2023-12-04 17:54:35 25 4
gpt4 key购买 nike

有人可以向我解释(或重定向到资源)为什么在这种特殊情况下没有“正确”生成类型标签:

class A(s: Seq[_]*)

def toto[T: TypeTag](p: Seq[T]): Seq[T] = {
println(typeTag[T].tpe)
p
}

val data = Seq( ("a", "a") )
val x = data.map(_._1)
new A(
toto(x),
toto(data.map(_._2)),
toto[String](data.map(_._2))
)

// output:
// java.lang.String
// Any
// String

据我所知,由于我的类 A 采用“无类型”(以及存在类型)序列,因此编译器在不需要明确要求时不会生成正确的类型标记(虽然它确实知道 data.map(_._2) 的类型,但它仍然使用 TypeTag[Any]... )。但它看起来很奇怪,我想知道是否对这种现象有更科学的解释。

此外,即使我不想创建特殊变量(如上面的 x 变量),我如何强制编译器生成正确的 TypeTag[String] )?

最佳答案

好问题!我有一个解释,但我不确定它是否正确(比方说 80%)。

与 Scala 类型推断问题一样,您需要了解预期类型。在这种情况下,new A 的所有参数都使用预期类型 Seq[_] 进行类型化,这与 Seq[Any] 相同,因为的协方差。所以:

  1. toto(data.map(_._2)) 的类型为预期类型 Seq[Any]data.map(_._2) 的类型为预期类型 Seq[Any]Seq#map的签名是

    def map[B, That](f: A => B)(implicit bf: CanBuildFrom[Seq[A], B, That]): That 

    so That 是根据预期类型推断的,并找到合适的隐式 bf。我实际上不确定 B 是否被推断为 StringAny,但这可能无关紧要。

  2. val x = data.map(_._1) 中,没有预期的类型,因此 B 被推断为 String,根据AB找到隐式bf,然后从完整类型推断That bf 的。

  3. toto(x) 的类型为预期类型 Seq[Any]x 的类型为预期类型 Seq[Any],但它已经具有类型 Seq[String],预期类型无关紧要。

关于Scala 2.11.8 类型标签并不总是由编译器正确生成,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49303107/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com