Scala更高的kinded类型方差
发布时间:2020-12-16 18:36:54 所属栏目:安全 来源:网络整理
导读:我正在用更高级的类型浸泡我的脚趾,探索一个非常基本的 Scala示例: trait Mappable[F[_]] { def map[A,B](fa: F[A])(f: A = B): F[B]}object Mappable { implicit object MappableOption extends Mappable[Option] { def map[A,B](fa: Option[A])(f: A = B)
我正在用更高级的类型浸泡我的脚趾,探索一个非常基本的
Scala示例:
trait Mappable[F[_]] { def map[A,B](fa: F[A])(f: A => B): F[B] } object Mappable { implicit object MappableOption extends Mappable[Option] { def map[A,B](fa: Option[A])(f: A => B): Option[B] = fa.map(f) } implicit object MappableSeq extends Mappable[Seq] { def map[A,B](fa: Seq[A])(f: A => B): Seq[B] = fa.map(f) } } def bananaTuple[F[_],T](f: F[T])(implicit F: Mappable[F]): F[(String,T)] = F.map(f)(("banana",_)) 这有效: bananaTuple(Option(42)) // Some((banana,42)) bananaTuple(Seq(42)) // List((banana,42)) 但这不编译: bananaTuple(Some(42)) bananaTuple(List(42)) 我得到的编译错误: could not find implicit value for parameter F: ch.netzwerg.hkt.HigherKindedTypes.Mappable[Some] bananaTuple(Some(42)) not enough arguments for method bananaTuple: (implicit F: ch.netzwerg.hkt.HigherKindedTypes.Mappable[Some])Some[(String,Int)]. Unspecified value parameter F. bananaTuple(Some(42)) 如何在游戏中带来变化? 解决方法
我们可以使用更多参数多态来完成这项工作:
object MappableExample { trait Mappable[F[_]] { type Res[_] def map[A,B](f: A => B)(c: F[A]): Res[B] } implicit def seqMappable[C[X] <: Seq[X]] = new Mappable[C] { type Res[X] = Seq[X] override def map[A,B](f:A => B)(c: C[A]): Seq[B] = c.map(f) } implicit def optionMappable[C[X] <: Option[X]]: Mappable[C] = new Mappable[C] { type Res[X] = Option[X] override def map[A,B](f: A => B)(c: C[A]): Option[B] = c.map(f) } def map[A,B,C[_]](xs: C[A])(f: A => B)(implicit mappable: Mappable[C]): mappable.Res[B] = { mappable.map(f)(xs) } def main(args: Array[String]): Unit = { println(map(List(1,2,3))(("banana",_))) println(map(Some(1))(("banana",_))) } } 产量: List((banana,1),(banana,2),3)) Some((banana,1)) 编译器现在将Some推断为Mappable [Some] #Res [Int]和Mappable [List] #Res [Int],这非常难看.人们可以期望编译器实际上能够推断出正确的类型,而不需要对Mappable特性进行任何协变/反演,这是我们无法做到的,因为我们在不变的位置使用它. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |