Could not find implicit value for evidence parameter of type scala.reflect.ClassManifest[T]

前端 未结 2 1498
庸人自扰
庸人自扰 2021-02-12 14:24

It seems I don\'t understand something important, maybe about erasure (damn it).

I have a method, which I wanted to create array of size n filled with value

2条回答
  •  北荒
    北荒 (楼主)
    2021-02-12 15:07

    The Array.fill method has the following signature:

    def fill[T](n: Int)(elem: => T)(implicit arg0: ClassManifest[T]): Array[T]
    

    In order to get an instance of ClassManifest[T] you need to know the concrete type. A ClassManifest can be obtained like this:

    implicitly[ClassManifest[String]]
    

    A ClassManifest is implicitly available for every concrete type.

    For any implicit error, you can add the implicits you require to the method with the type parameter:

    def wrap[T](n:Int)(elem: => T)(implicit c:ClassManifest[T], o:Ordering[T])
    

    If you did not yourself introduce ClassManifest or Ordering, the writers of the library have (most likely) provided sensible defaults for you.

    If you would call the wrap method:

    wrap(2)(3)
    

    It's expanded like this:

    wrap[Int](2)(3)(implicitly[ClassManifest[Int]], implicitly[Ordering[Int]])
    

    If you introduced a custom class Person here, you would get an error for not finding an implicit instance of Ordering[Person]. The writers of the library could not have known how to order Person. You could solve that like this:

    class Person
    
    implicit val o = new Ordering[Person] { // implement required methods }
    
    wrap(2)(new Person)
    

    The Scala compiler looks in different scopes for implicits, an Ordering would usually not be specified like this. I suggest you look up implicit resolution on the internet to learn more about it.

提交回复
热议问题