@@ -631,12 +631,17 @@ trait Applications extends Compatibility {
631
631
* - "does not have parameter" if a named parameter does not mention a formal
632
632
* parameter name.
633
633
*/
634
- def reorder [T <: Untyped ](args : List [Trees .Tree [T ]]): List [Trees .Tree [T ]] = {
634
+ def reorder [T <: Untyped ](args : List [Trees .Tree [T ]]): List [Trees .Tree [T ]] =
635
635
636
- /** @param pnames The list of parameter names that are missing arguments
636
+ inline def tailOf [A ](list : List [A ]): List [A ] = if list.isEmpty then list else list.tail // list.drop(1)
637
+
638
+ /** Reorder the suffix of named args per a list of required names.
639
+ *
640
+ * @param pnames The list of parameter names that are missing arguments
637
641
* @param args The list of arguments that are not yet passed, or that are waiting to be dropped
638
642
* @param nameToArg A map from as yet unseen names to named arguments
639
- * @param toDrop A set of names that have already be passed as named arguments
643
+ * @param toDrop A set of names that have already been passed as named arguments
644
+ * @param missingArgs true if args were already missing, so error on positional
640
645
*
641
646
* For a well-typed application we have the invariants
642
647
*
@@ -645,49 +650,46 @@ trait Applications extends Compatibility {
645
650
*/
646
651
def handleNamed (pnames : List [Name ], args : List [Trees .Tree [T ]],
647
652
nameToArg : Map [Name , Trees .NamedArg [T ]], toDrop : Set [Name ],
648
- missingArgs : Boolean ): List [Trees .Tree [T ]] = pnames match {
649
- case pname :: pnames1 if nameToArg contains pname =>
653
+ missingArgs : Boolean ): List [Trees .Tree [T ]] = pnames match
654
+ case pname :: pnames if nameToArg. contains( pname) =>
650
655
// there is a named argument for this parameter; pick it
651
- nameToArg(pname) :: handleNamed(pnames1 , args, nameToArg - pname, toDrop + pname, missingArgs)
656
+ nameToArg(pname) :: handleNamed(pnames , args, nameToArg - pname, toDrop + pname, missingArgs)
652
657
case _ =>
653
- def pnamesRest = if (pnames.isEmpty) pnames else pnames.tail
654
- args match {
658
+ args match
655
659
case (arg @ NamedArg (aname, _)) :: args1 =>
656
- if ( toDrop contains aname) // argument is already passed
657
- handleNamed(pnames, args1, nameToArg, toDrop - aname, missingArgs)
658
- else if (( nameToArg contains aname) && pnames.nonEmpty) // argument is missing, pass an empty tree
659
- genericEmptyTree :: handleNamed(pnames.tail, args, nameToArg, toDrop, missingArgs = true )
660
- else { // name not (or no longer) available for named arg
660
+ if toDrop. contains( aname) // named argument is already passed
661
+ then handleNamed(pnames, args1, nameToArg, toDrop - aname, missingArgs)
662
+ else if nameToArg. contains( aname) && pnames.nonEmpty // argument is missing, pass an empty tree
663
+ then genericEmptyTree :: handleNamed(pnames.tail, args, nameToArg, toDrop, missingArgs = true )
664
+ else // name not (or no longer) available for named arg
661
665
def msg =
662
- if ( methodType.paramNames contains aname)
666
+ if methodType.paramNames. contains( aname) then
663
667
em " parameter $aname of $methString is already instantiated "
664
668
else
665
669
em " $methString does not have a parameter $aname"
666
670
fail(msg, arg.asInstanceOf [Arg ])
667
- arg :: handleNamed(pnamesRest, args1, nameToArg, toDrop, missingArgs)
668
- }
669
- case arg :: args1 =>
671
+ arg :: handleNamed(tailOf(pnames), args1, nameToArg, toDrop, missingArgs)
672
+ case arg :: args =>
670
673
if toDrop.nonEmpty || missingArgs then
671
674
report.error(i " positional after named argument " , arg.srcPos)
672
- arg :: handleNamed(pnamesRest, args1, nameToArg, toDrop, missingArgs) // unnamed argument; pick it
673
- case Nil => // no more args, continue to pick up any preceding named args
674
- if (pnames.isEmpty) Nil
675
- else handleNamed(pnamesRest, args, nameToArg, toDrop, missingArgs)
676
- }
677
- }
675
+ arg :: handleNamed(tailOf(pnames), args, nameToArg, toDrop, missingArgs) // unnamed argument; pick it
676
+ case nil => // no more args, continue to pick up any preceding named args
677
+ if pnames.isEmpty then nil
678
+ else handleNamed(tailOf(pnames), nil, nameToArg, toDrop, missingArgs)
678
679
680
+ /** Skip prefix of positional args, then handleNamed */
679
681
def handlePositional (pnames : List [Name ], args : List [Trees .Tree [T ]]): List [Trees .Tree [T ]] =
680
- args match {
681
- case (arg : NamedArg @ unchecked ) :: _ =>
682
- val nameAssocs = for ( case arg @ NamedArg (name, _) <- args) yield (name, arg)
683
- handleNamed(pnames, args, nameAssocs.toMap, toDrop = Set (), missingArgs = false )
684
- case arg :: args1 =>
685
- arg :: handlePositional( if (pnames.isEmpty) Nil else pnames.tail, args1)
686
- case Nil => Nil
687
- }
682
+ args match
683
+ case (_ : NamedArg ) :: _ =>
684
+ // val nameAssocs = for case arg @ NamedArg(name, _) <- args yield (name, arg)
685
+ val nameAssocs = args.collect { case arg @ NamedArg (name, _) => name -> arg }
686
+ handleNamed(pnames, args, nameAssocs.toMap, toDrop = Set .empty, missingArgs = false )
687
+ case arg :: args =>
688
+ arg :: handlePositional(tailOf(pnames), args)
689
+ case nil => nil
688
690
689
691
handlePositional(methodType.paramNames, args)
690
- }
692
+ end reorder
691
693
692
694
/** Is `sym` a constructor of a Java-defined annotation? */
693
695
def isJavaAnnotConstr (sym : Symbol ): Boolean =
0 commit comments