summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorMartin Odersky <odersky@gmail.com>2010-04-12 11:52:39 +0000
committerMartin Odersky <odersky@gmail.com>2010-04-12 11:52:39 +0000
commitcfe47e4b74cc166af31cc130b0830112c46bdc61 (patch)
tree7716cb0c8cb0179f0b09328779e0c2ac06621025 /src
parentbed1ffb1c357e09c05ea6a58bd19a75510f1822e (diff)
downloadscala-cfe47e4b74cc166af31cc130b0830112c46bdc61.tar.gz
scala-cfe47e4b74cc166af31cc130b0830112c46bdc61.tar.bz2
scala-cfe47e4b74cc166af31cc130b0830112c46bdc61.zip
Closes #3224. Review by retronym.
Diffstat (limited to 'src')
-rw-r--r--src/compiler/scala/tools/nsc/typechecker/Infer.scala15
-rw-r--r--src/compiler/scala/tools/nsc/typechecker/Typers.scala6
2 files changed, 16 insertions, 5 deletions
diff --git a/src/compiler/scala/tools/nsc/typechecker/Infer.scala b/src/compiler/scala/tools/nsc/typechecker/Infer.scala
index c0b54cb4f0..c8d3308077 100644
--- a/src/compiler/scala/tools/nsc/typechecker/Infer.scala
+++ b/src/compiler/scala/tools/nsc/typechecker/Infer.scala
@@ -802,6 +802,14 @@ trait Infer {
(argtpes1, argPos, namesOK)
}
+ /** don't do a () to (()) conversion for methods whose second parameter
+ * is a varargs. This is a fairly kludgey way to address #3224.
+ * We'll probably find a better way to do this by identifying
+ * tupled and n-ary methods, but thiws is something for a future major revision.
+ */
+ def isUnitForVarArgs(args: List[AnyRef], params: List[Symbol]): Boolean =
+ args.length == 0 && params.length == 2 && isVarArgs(params)
+
/** Is there an instantiation of free type variables <code>undetparams</code>
* such that function type <code>ftpe</code> is applicable to
* <code>argtpes</code> and its result conform to <code>pt</code>?
@@ -833,14 +841,15 @@ trait Infer {
def tryTupleApply: Boolean = {
// if 1 formal, 1 argtpe (a tuple), otherwise unmodified argtpes0
- val tupleArgTpe = actualTypes(argtpes0 map {
+ val tupleArgTpes = actualTypes(argtpes0 map {
// no assignment is treated as named argument here
case NamedType(name, tp) => UnitClass.tpe
case tp => tp
}, formals.length)
- argtpes0.length != tupleArgTpe.length &&
- isApplicable(undetparams, ftpe, tupleArgTpe, pt)
+ argtpes0.length != tupleArgTpes.length &&
+ !isUnitForVarArgs(argtpes0, params) &&
+ isApplicable(undetparams, ftpe, tupleArgTpes, pt)
}
def typesCompatible(argtpes: List[Type]) = {
val restpe = ftpe.resultType(argtpes)
diff --git a/src/compiler/scala/tools/nsc/typechecker/Typers.scala b/src/compiler/scala/tools/nsc/typechecker/Typers.scala
index 284b12e501..3fe937f241 100644
--- a/src/compiler/scala/tools/nsc/typechecker/Typers.scala
+++ b/src/compiler/scala/tools/nsc/typechecker/Typers.scala
@@ -2327,12 +2327,14 @@ trait Typers { self: Analyzer =>
// if 1 formal, 1 arg (a tuple), otherwise unmodified args
val tupleArgs = actualArgs(tree.pos.makeTransparent, args, formals.length)
- if (tupleArgs.length != args.length) {
+ if (tupleArgs.length != args.length && !isUnitForVarArgs(args, params)) {
// expected one argument, but got 0 or >1 ==> try applying to tuple
// the inner "doTypedApply" does "extractUndetparams" => restore when it fails
val savedUndetparams = context.undetparams
silent(_.doTypedApply(tree, fun, tupleArgs, mode, pt)) match {
- case t: Tree => Some(t)
+ case t: Tree =>
+// println("tuple conversion to "+t+" for "+mt)//DEBUG
+ Some(t)
case ex =>
context.undetparams = savedUndetparams
None