title: Scala: how does List[Double] differ from a List[Int] that is casted to List[Double]?
body: <p>The following code compiles fine but crashes at runtime (tested with scala 2.9.2).</p>
  
  <pre><code>object Test {
  
      def fun(x:Double) : Double = { 1.234 * x }
  
      def main(args: Array[String]) {
          val l1 = List(1.0, 2.0, 3.0)
          val lfun1 = l1 map fun
          println(lfun1)
  
          val l2 = List(1, 2, 3).asInstanceOf[List[Double]]
          val lfun2 = l2 map fun // &lt;--- crashes
          println(lfun2)
      }
  }
  </code></pre>
  
  <p>Output:</p>
  
  <pre><code>List(1.234, 2.468, 3.702)
  Exception in thread "main" java.lang.ClassCastException: java.lang.Integer cannot be cast to java.lang.Double
      at scala.runtime.BoxesRunTime.unboxToDouble(BoxesRunTime.java:114)
      at Test$$anonfun$2.apply(Covariance.scala:11)
      at scala.collection.immutable.List.map(List.scala:273)
      at Test$.main(Covariance.scala:11)
      at Test.main(Covariance.scala)
  </code></pre>
  
  <p>See the REPL output below for more details.</p>
  
  <p>I come from Java and want to learn Scala, so can somebody please explain to me the reasoning why it crashes and why the compiler cannot detect this? I suppose this has something to do with "views" (Int versus Double) or with "covariance" (List[Int] as List[Double]), but I do not get the point.</p>
  
  <hr>
  
  <p>Here is the individual output in the Scala REPL:</p>
  
  <pre><code>scala&gt; def fun(x:Double) : Double = { 1.234 * x }
  fun: (x: Double)Double
  
  scala&gt; val l1 = List(1.0, 2.0, 3.0)
  l1: List[Double] = List(1.0, 2.0, 3.0)
  
  scala&gt; val lfun1 = l1 map fun
  lfun1: List[Double] = List(1.234, 2.468, 3.702)
  
  scala&gt; println(lfun1)
  List(1.234, 2.468, 3.702)
  
  scala&gt; val l2 = List(1, 2, 3).asInstanceOf[List[Double]]
  l2: List[Double] = List(1, 2, 3)
  
  scala&gt; val lfun2 = l2 map fun
  java.lang.ClassCastException: java.lang.Integer cannot be cast to java.lang.Double
      at scala.runtime.BoxesRunTime.unboxToDouble(Unknown Source)
      at $anonfun$1.apply(&lt;console&gt;:9)
      at scala.collection.TraversableLike$$anonfun$map$1.apply(TraversableLike.scala:233)
      at scala.collection.TraversableLike$$anonfun$map$1.apply(TraversableLike.scala:233)
      at scala.collection.LinearSeqOptimized$class.foreach(LinearSeqOptimized.scala:59)
      at scala.collection.immutable.List.foreach(List.scala:76)
      at scala.collection.TraversableLike$class.map(TraversableLike.scala:233)
      at scala.collection.immutable.List.map(List.scala:76)
      at .&lt;init&gt;(&lt;console&gt;:9)
      at .&lt;clinit&gt;(&lt;console&gt;)
      at .&lt;init&gt;(&lt;console&gt;:11)
      at .&lt;clinit&gt;(&lt;console&gt;)
      at $print(&lt;console&gt;)
      at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
      at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
      at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
      at java.lang.reflect.Method.invoke(Method.java:606)
      at scala.tools.nsc.interpreter.IMain$ReadEvalPrint.call(IMain.scala:704)
      at scala.tools.nsc.interpreter.IMain$Request$$anonfun$14.apply(IMain.scala:920)
      at scala.tools.nsc.interpreter.Line$$anonfun$1.apply$mcV$sp(Line.scala:43)
      at scala.tools.nsc.io.package$$anon$2.run(package.scala:25)
      at java.lang.Thread.run(Thread.java:745)
  </code></pre>