Skip to content

Commit e3b3f6a

Browse files
committed
Fix #2916: Reorder parameters
1 parent 9fd4d31 commit e3b3f6a

File tree

3 files changed

+92
-2
lines changed

3 files changed

+92
-2
lines changed

compiler/src/dotty/tools/dotc/typer/Applications.scala

Lines changed: 27 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ package dotc
33
package typer
44

55
import core._
6-
import ast.{Trees, untpd, tpd, TreeInfo}
6+
import ast.{TreeInfo, Trees, tpd, untpd}
77
import util.Positions._
88
import util.Stats.track
99
import Trees.Untyped
@@ -24,13 +24,17 @@ import NameKinds.DefaultGetterName
2424
import ProtoTypes._
2525
import EtaExpansion._
2626
import Inferencing._
27+
2728
import collection.mutable
28-
import config.Printers.{typr, unapp, overload}
29+
import config.Printers.{overload, typr, unapp}
2930
import TypeApplications._
31+
3032
import language.implicitConversions
3133
import reporting.diagnostic.Message
3234
import Constants.{Constant, IntTag, LongTag}
3335

36+
import scala.collection.mutable.ListBuffer
37+
3438
object Applications {
3539
import tpd._
3640

@@ -611,7 +615,28 @@ trait Applications extends Compatibility { self: Typer with Dynamic =>
611615
liftFun()
612616
val eqSuffixLength = firstDiff(app.args.reverse, orderedArgs.reverse)
613617
val (liftable, rest) = typedArgs splitAt (typedArgs.length - eqSuffixLength)
618+
619+
var indices = ListBuffer.empty[Int]
620+
var nextDefaultParamIndex = args.size
621+
var prefixShift = 0
622+
if (liftedDefs.nonEmpty) {
623+
indices += 0
624+
prefixShift = 1
625+
}
626+
for (l <- liftable) {
627+
if (!args.contains(l)) {
628+
indices += prefixShift + nextDefaultParamIndex
629+
nextDefaultParamIndex += 1
630+
}
631+
else indices += prefixShift + args.indexOf(l)
632+
}
633+
614634
typedArgs = liftArgs(liftedDefs, methType, liftable) ++ rest
635+
636+
assert(liftedDefs.size == indices.size)
637+
val newOrder = (liftedDefs zip indices).sortBy(_._2).unzip._1.toList
638+
liftedDefs = ListBuffer.empty
639+
liftedDefs ++= newOrder
615640
}
616641
if (sameSeq(typedArgs, args)) // trick to cut down on tree copying
617642
typedArgs = args.asInstanceOf[List[Tree]]

tests/run/i2916.check

Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
1
2+
2
3+
3
4+
4
5+
5
6+
7+
1
8+
2
9+
3
10+
4
11+
5
12+
13+
1
14+
3
15+
2
16+
4
17+
5
18+
19+
1
20+
3
21+
5
22+
2
23+
4
24+
25+
1
26+
3
27+
4
28+
2
29+
5
30+
31+
0
32+
1
33+
3
34+
4
35+
2
36+
5
37+
38+
0
39+
1
40+
3
41+
4
42+
2
43+
5

tests/run/i2916.scala

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
object Test {
2+
def p(x: Int) = { println(x); x }
3+
def foo(x1: Int, x2: Int, x3: Int, x4: Int = p(4), x5: Int = p(5)) = 1
4+
def main(args: Array[String]) = {
5+
foo(p(1), p(2), p(3)) // 1 2 3 4 5
6+
println()
7+
foo(p(1), x2 = p(2), x3 = p(3)) // 1 2 3 4 5
8+
println()
9+
foo(p(1), x3 = p(3), x2 = p(2)) // 1 3 2 4 5
10+
println()
11+
foo(p(1), x3 = p(3), x5 = p(5), x2 = p(2)) // 1 3 5 2 4
12+
println()
13+
foo(p(1), x3 = p(3), x4 = p(4), x2 = p(2)) // 1 3 4 2 5
14+
println()
15+
16+
def test = { println(0); Test }
17+
test.foo(p(1), x3 = p(3), x4 = p(4), x2 = p(2)) // 0 1 3 4 2 5
18+
println()
19+
20+
{ println(0); Test }.foo(p(1), x3 = p(3), x4 = p(4), x2 = p(2)) // 0 1 3 4 2 5
21+
}
22+
}

0 commit comments

Comments
 (0)