diff options
author | Denys Shabalin <denys.shabalin@typesafe.com> | 2014-01-16 12:01:30 +0100 |
---|---|---|
committer | Denys Shabalin <denys.shabalin@typesafe.com> | 2014-01-16 12:45:38 +0100 |
commit | 8e9862473abd03bded2d3afa60c777099f7872c5 (patch) | |
tree | df2b1fcbd893a77ea63717f6290146357214b3cf /src/reflect | |
parent | 393829489a1e352c2ed659b16b6bea24069f4f9a (diff) | |
download | scala-8e9862473abd03bded2d3afa60c777099f7872c5.tar.gz scala-8e9862473abd03bded2d3afa60c777099f7872c5.tar.bz2 scala-8e9862473abd03bded2d3afa60c777099f7872c5.zip |
SI-8076 improve support for implicit argument list
This adds support for construction and deconstruction
of implicit argument list which was originally suggested
by @cvogt.
1. Splicing vale into implicit argument list automatically
adds implicit flag to them:
val x = q"val x: Int"
q"def foo(implicit $x)"
// <=> q"def foo(implicit x: Int)"
2. One might extract implicit argument list separately from
other argument lists:
val q”def foo(...$argss)(implicit ..$impl)" =
q"def foo(implicit x: Int)
// argss is Nil, impl contains valdef for x
But this doesn't require you to always extract it separatly:
val q”def foo(...$argss)" =
q"def foo(implicit x: Int)
// argss contains valdef for x
Diffstat (limited to 'src/reflect')
-rw-r--r-- | src/reflect/scala/reflect/api/BuildUtils.scala | 7 | ||||
-rw-r--r-- | src/reflect/scala/reflect/internal/BuildUtils.scala | 14 | ||||
-rw-r--r-- | src/reflect/scala/reflect/internal/StdNames.scala | 1 |
3 files changed, 22 insertions, 0 deletions
diff --git a/src/reflect/scala/reflect/api/BuildUtils.scala b/src/reflect/scala/reflect/api/BuildUtils.scala index 89492e75c4..d70fa01ae6 100644 --- a/src/reflect/scala/reflect/api/BuildUtils.scala +++ b/src/reflect/scala/reflect/api/BuildUtils.scala @@ -94,6 +94,13 @@ private[reflect] trait BuildUtils { self: Universe => def freshTypeName(prefix: String): TypeName + val ImplicitParams: ImplicitParamsExtractor + + trait ImplicitParamsExtractor { + def apply(paramss: List[List[ValDef]], implparams: List[ValDef]): List[List[ValDef]] + def unapply(vparamss: List[List[ValDef]]): Some[(List[List[ValDef]], List[ValDef])] + } + val ScalaDot: ScalaDotExtractor trait ScalaDotExtractor { diff --git a/src/reflect/scala/reflect/internal/BuildUtils.scala b/src/reflect/scala/reflect/internal/BuildUtils.scala index 657b098952..292413674b 100644 --- a/src/reflect/scala/reflect/internal/BuildUtils.scala +++ b/src/reflect/scala/reflect/internal/BuildUtils.scala @@ -86,6 +86,10 @@ trait BuildUtils { self: SymbolTable => """consider reformatting it into q"val $name: $T = $default" shape""") } + def mkImplicitParam(args: List[Tree]): List[ValDef] = args.map(mkImplicitParam) + + def mkImplicitParam(tree: Tree): ValDef = mkParam(tree, IMPLICIT | PARAM) + def mkTparams(tparams: List[Tree]): List[TypeDef] = tparams.map { case td: TypeDef => copyTypeDef(td)(mods = (td.mods | PARAM) & (~DEFERRED)) @@ -143,6 +147,16 @@ trait BuildUtils { self: SymbolTable => protected implicit def fresh: FreshNameCreator = self.currentFreshNameCreator + object ImplicitParams extends ImplicitParamsExtractor { + def apply(paramss: List[List[ValDef]], implparams: List[ValDef]): List[List[ValDef]] = + if (implparams.nonEmpty) paramss :+ mkImplicitParam(implparams) else paramss + + def unapply(vparamss: List[List[ValDef]]): Some[(List[List[ValDef]], List[ValDef])] = vparamss match { + case init :+ (last @ (initlast :: _)) if initlast.mods.isImplicit => Some((init, last)) + case _ => Some((vparamss, Nil)) + } + } + object FlagsRepr extends FlagsReprExtractor { def apply(bits: Long): FlagSet = bits def unapply(flags: Long): Some[Long] = Some(flags) diff --git a/src/reflect/scala/reflect/internal/StdNames.scala b/src/reflect/scala/reflect/internal/StdNames.scala index 73ad9def73..49c26ca58d 100644 --- a/src/reflect/scala/reflect/internal/StdNames.scala +++ b/src/reflect/scala/reflect/internal/StdNames.scala @@ -576,6 +576,7 @@ trait StdNames { val Flag : NameType = "Flag" val FlagsRepr: NameType = "FlagsRepr" val Ident: NameType = "Ident" + val ImplicitParams: NameType = "ImplicitParams" val Import: NameType = "Import" val Literal: NameType = "Literal" val LiteralAnnotArg: NameType = "LiteralAnnotArg" |