I am working on what should be a trivial piece of code. I want to take a List, and convert it to an equivalent Array:
import scala.collection.JavaConverters
object Help extends App {
def f1[T](lst: List[T]) = {
lst.toArray
}
val x = List(1, 2, 3)
println(f1(x))
}
Running this code gives:
"No ClassTag available for T"
How can I avoid this problem; I am coming from a Python background so would appreciate a response that gives me an understanding of the mechanics here.
Thank you!
Try adding implicit
ClassTag
parameter like soThe reason is clear if we have a look at signature of
toArray
which is equivalent to
so you have to thread the implicit parameter from
f1
down totoArray
.The key is to understand
Array
is not a true Scala collection. For once, it is not a subtype ofIterable
Another difference between
Array
and true Scala collections is the absence of need forClassTag
for true Scala collections. The reason for this is Scala collections go through a process of type erasure which means runtime knows it is aList
but does not differentiate betweenList[Int]
andList[String]
, for example. However this does not hold forArray
. At runtime there is indeed a difference betweenArray[Int]
andArray[String]
. HenceClassTag
is a mechanism invented to carry type information, which exists only at compile-time, over to runtime, soArray
can have the behaviour as in Java.You will encounter other differences, for example
Best practice is to avoid
Array
if possible.