【问题标题】:Implicit conversion from array to list从数组到列表的隐式转换
【发布时间】:2011-02-13 04:30:01
【问题描述】:

如何编写从Array[_]List[_] 类型的隐式转换?我尝试了以下方法,但似乎不起作用。

scala> implicit def arrayToList[A : ClassManifest](a: Array[A]): List[A] = a.toList
<console>:5: error: type mismatch;
 found   : Array[A]
 required: ?{val toList: ?}
Note that implicit conversions are not applicable because they are ambiguous:
 both method arrayToList in object $iw of type [A](a: Array[A])(implicit evidence$1: ClassManifest[A])List[A]
 and method genericArrayOps in object Predef of type [T](xs: Array[T])scala.collection.mutable.ArrayOps[T]
 are possible conversion functions from Array[A] to ?{val toList: ?}
       implicit def arrayToList[A : ClassManifest](a: Array[A]): List[A] = a.toList
                                                                           ^

【问题讨论】:

    标签: scala implicit-conversion


    【解决方案1】:
    implicit def arrayToList[A](a: Array[A]) = a.toList
    

    似乎按预期工作。我的猜测是Predef 中已经有一个genericArrayOps 具有从Array[T] -&gt; ArrayOps[T] 进行隐式转换的签名,ArrayOps[T] 有一个方法.toList(): List[T]。您的方法具有签名Array[T] -&gt; List[T],这也使方法.toList[T] 可用。正文要求使用该签名进行隐式转换。编译器不知道使用 arrayToList 会使该方法进入无限循环,因此会出现歧义错误。但是,类型推断返回类型似乎能够解决这个问题。隐式解析似乎与类型推断不太吻合。

    另外值得注意的是,由于默认情况下已经有一个隐式转换可以让你得到你想要的,所以不需要从ArrayList 的隐式转换。

    【讨论】:

    • 命名约定XxxOps 总是暗示您看到Xxx 类型的pimped 扩展方法
    • 这对我很有用。我有一个可能为空的数组(从 JDBC 调用返回,所以 Option 不是一个选项),并且使用您的解释/解决方法我能够创建一个隐式来处理它:implicit def nullableArrayToList[T](array: Array[T]) Option(array).fold(List.empty[T]) { _.toList }
    【解决方案2】:

    数组转换时不需要ManifestClassManifest,因为Array 是一种在JVM 上得到特殊处理且不经过处理的“集合”类型键入擦除。

    这意味着您可以采用明显/琐碎的方法,无需任何技巧:

    implicit def arrayToList[A](arr: Array[A]) = arr.toList
    

    但有一个问题...鉴于.toList 已经是一个如此微不足道的操作,将其隐式化有什么好处?

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-08-25
      • 2016-05-19
      • 2015-09-16
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多