Dotty: REPL: chained extension methods can only be called once

Created on 20 Oct 2020  路  4Comments  路  Source: lampepfl/dotty

Minimized code

Only in the REPL, it seems like calling a chain of extension methods has a strange side effect that prevents it from happening again

scala> IArray(1,2,3).reverse.sorted                                                                                   
val res0: opaques.IArray[Int] = Array(1, 2, 3)

scala> IArray(1,2,3).reverse.sorted                                                                                   
1 |IArray(1,2,3).reverse.sorted
  |^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  |value sorted is not a member of scala.opaques.IArray[Int].
  |An extension method was tried, but could not be fully constructed:
  |
  |    genericArrayOps[T](
  |      opaques.arrayOps.extension_reverse[Int](
  |        {
  |          Array.apply(
  |            {
  |              1
  |            }
  |          , 
  |            {
  |              [2,3 : Int]:Int*
  |            }:Int*
  |          ).asInstanceOf[opaques.IArray[Int]]:IArray[Int]
  |        }
  |      )
  |    )

scala> 

Expectation

this is ok when they are called one after the other in a source file

repl bug

Most helpful comment

Still broken on M3 and also current master

[success] Total time: 126 s (02:06), completed Dec 27, 2020, 9:32:57 AM
Starting scala3 REPL...
scala>

scala> IArray(1,2,3).reverse.sorted
val res0: opaques.IArray[Int] = Array(1, 2, 3)

scala> IArray(1,2,3).reverse.sorted
1 |IArray(1,2,3).reverse.sorted
  |^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  |value sorted is not a member of scala.opaques.IArray[Int].
  |An extension method was tried, but could not be fully constructed:
  |
  |    copyArrayToImmutableIndexedSeq[T](
  |      opaques.arrayOps.reverse[Int](
  |        Array.apply(1, [2,3 : Int]:Int*:Int*).asInstanceOf[opaques.IArray[Int]]:
  |          IArray[Int]
  |      )
  |    )

scala>  

also per previous comment

scala> IArray(1,2,3).reverse
val res0: opaques.IArray[Int] = Array(3, 2, 1)

scala> IArray(1,2,3).reverse
val res1: scala.opaques.IArray[Int] = Array(3, 2, 1)

scala> IArray(1,2,3).reverse.sorted
1 |IArray(1,2,3).reverse.sorted
  |^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  |value sorted is not a member of scala.opaques.IArray[Int].
  |An extension method was tried, but could not be fully constructed:
  |
  |    genericArrayOps[T](
  |      opaques.arrayOps.reverse[Int](
  |        Array.apply(1, [2,3 : Int]:Int*:Int*).asInstanceOf[opaques.IArray[Int]]:
  |          IArray[Int]
  |      )
  |    )

scala> (IArray(1,2,3).reverse: opaques.IArray[Int]).sorted
val res2: scala.opaques.IArray[Int] = Array(1, 2, 3)

scala> (IArray(1,2,3).reverse: scala.opaques.IArray[Int]).sorted
val res3: scala.opaques.IArray[Int] = Array(1, 2, 3)

scala> (IArray(1,2,3).reverse: IArray[Int]).sorted
val res4: scala.opaques.IArray[Int] = Array(1, 2, 3)

scala> 

All 4 comments

@anatoliykmetyuk Not sure who to assign this to, are you the most knowledgeable person on REPL at the moment?

The type seems to change subtly.

scala> IArray(1,2,3).reverse
val res0: opaques.IArray[Int] = Array(3, 2, 1)

scala> IArray(1,2,3).reverse
val res1: scala.opaques.IArray[Int] = Array(3, 2, 1)

Also

scala> IArray.emptyIntIArray.reverse
val res0: opaques.IArray[Int] = Array()

scala> IArray.emptyIntIArray.reverse
1 |IArray.emptyIntIArray.reverse
  |^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  |value reverse is not a member of opaques.IArray[Int].
  |An extension method was tried, but could not be fully constructed:
  |
  |    opaques.arrayOps.reverse[T](IArray.emptyIntIArray)

Seems to work in 3.0-M3

Still broken on M3 and also current master

[success] Total time: 126 s (02:06), completed Dec 27, 2020, 9:32:57 AM
Starting scala3 REPL...
scala>

scala> IArray(1,2,3).reverse.sorted
val res0: opaques.IArray[Int] = Array(1, 2, 3)

scala> IArray(1,2,3).reverse.sorted
1 |IArray(1,2,3).reverse.sorted
  |^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  |value sorted is not a member of scala.opaques.IArray[Int].
  |An extension method was tried, but could not be fully constructed:
  |
  |    copyArrayToImmutableIndexedSeq[T](
  |      opaques.arrayOps.reverse[Int](
  |        Array.apply(1, [2,3 : Int]:Int*:Int*).asInstanceOf[opaques.IArray[Int]]:
  |          IArray[Int]
  |      )
  |    )

scala>  

also per previous comment

scala> IArray(1,2,3).reverse
val res0: opaques.IArray[Int] = Array(3, 2, 1)

scala> IArray(1,2,3).reverse
val res1: scala.opaques.IArray[Int] = Array(3, 2, 1)

scala> IArray(1,2,3).reverse.sorted
1 |IArray(1,2,3).reverse.sorted
  |^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  |value sorted is not a member of scala.opaques.IArray[Int].
  |An extension method was tried, but could not be fully constructed:
  |
  |    genericArrayOps[T](
  |      opaques.arrayOps.reverse[Int](
  |        Array.apply(1, [2,3 : Int]:Int*:Int*).asInstanceOf[opaques.IArray[Int]]:
  |          IArray[Int]
  |      )
  |    )

scala> (IArray(1,2,3).reverse: opaques.IArray[Int]).sorted
val res2: scala.opaques.IArray[Int] = Array(1, 2, 3)

scala> (IArray(1,2,3).reverse: scala.opaques.IArray[Int]).sorted
val res3: scala.opaques.IArray[Int] = Array(1, 2, 3)

scala> (IArray(1,2,3).reverse: IArray[Int]).sorted
val res4: scala.opaques.IArray[Int] = Array(1, 2, 3)

scala> 
Was this page helpful?
0 / 5 - 0 ratings