From 9405c80db77e30e8c4f53c5d184392a92a9ae28c Mon Sep 17 00:00:00 2001 From: jvican Date: Fri, 1 Jul 2016 10:38:52 +0200 Subject: [PATCH] Widen type of final vars #1285 When defining a final var, the type is not widened and, thus, it's as specific as possible. However, when changing the value of the var, it will give a compilation error because it cannot match the constant types. This fix widens the type whenever it finds a final var. --- src/dotty/tools/dotc/typer/Typer.scala | 12 +++++++++++- tests/pos/WidenFinalVars.scala | 5 +++++ 2 files changed, 16 insertions(+), 1 deletion(-) create mode 100644 tests/pos/WidenFinalVars.scala diff --git a/src/dotty/tools/dotc/typer/Typer.scala b/src/dotty/tools/dotc/typer/Typer.scala index ae8900c435e3..ccbefa7fcce8 100644 --- a/src/dotty/tools/dotc/typer/Typer.scala +++ b/src/dotty/tools/dotc/typer/Typer.scala @@ -1008,7 +1008,7 @@ class Typer extends Namer with TypeAssigner with Applications with Implicits wit def typedValDef(vdef: untpd.ValDef, sym: Symbol)(implicit ctx: Context) = track("typedValDef") { val ValDef(name, tpt, _) = vdef completeAnnotations(vdef, sym) - val tpt1 = checkSimpleKinded(typedType(tpt)) + val tpt1 = widenIfFinalMutable(checkSimpleKinded(typedType(tpt)), sym) val rhs1 = vdef.rhs match { case rhs @ Ident(nme.WILDCARD) => rhs withType tpt1.tpe case rhs => typedExpr(rhs, tpt1.tpe) @@ -1018,6 +1018,16 @@ class Typer extends Namer with TypeAssigner with Applications with Implicits wit vdef1 } + /** Widen type if a valDef is both mutable and final, see #1285 */ + private def widenIfFinalMutable(vdef: Tree, sym: Symbol)(implicit ctx: Context) = { + if (sym.is(allOf(Mutable, Final))) { + val widened = vdef.tpe.widen + vdef.withType(widened) + sym.info_=(widened) + } + vdef + } + /** Add a @volitile to lazy vals when rewriting from Scala2 */ private def patchIfLazy(vdef: ValDef)(implicit ctx: Context): Unit = { val sym = vdef.symbol diff --git a/tests/pos/WidenFinalVars.scala b/tests/pos/WidenFinalVars.scala new file mode 100644 index 000000000000..446b42cd427b --- /dev/null +++ b/tests/pos/WidenFinalVars.scala @@ -0,0 +1,5 @@ +/* For more information, see #1285 */ +class Test { + final var x = false + x = true +} \ No newline at end of file