summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/reflect/scala/reflect/api/Names.scala30
-rw-r--r--src/reflect/scala/reflect/api/Trees.scala8
-rw-r--r--src/reflect/scala/reflect/internal/Names.scala10
-rw-r--r--src/reflect/scala/reflect/internal/Trees.scala2
-rw-r--r--test/files/scalacheck/ReflectionExtractors.scala52
5 files changed, 98 insertions, 4 deletions
diff --git a/src/reflect/scala/reflect/api/Names.scala b/src/reflect/scala/reflect/api/Names.scala
index 7c12f180a8..8add98d815 100644
--- a/src/reflect/scala/reflect/api/Names.scala
+++ b/src/reflect/scala/reflect/api/Names.scala
@@ -58,7 +58,7 @@ trait Names {
* Can be used for pattern matching, instance tests, serialization and likes.
* @group Tags
*/
-implicit val TypeNameTag: ClassTag[TypeName]
+ implicit val TypeNameTag: ClassTag[TypeName]
/** The abstract type of names representing types.
* @group Names
@@ -109,10 +109,38 @@ implicit val TypeNameTag: ClassTag[TypeName]
/** Create a new term name.
* @group Names
*/
+ @deprecated("Use TermName instead", "2.11.0")
def newTermName(s: String): TermName
/** Creates a new type name.
* @group Names
*/
+ @deprecated("Use TypeName instead", "2.11.0")
def newTypeName(s: String): TypeName
+
+ /** The constructor/extractor for `TermName` instances.
+ * @group Extractors
+ */
+ val TermName: TermNameExtractor
+
+ /** An extractor class to create and pattern match with syntax `TermName(s)`.
+ * @group Extractors
+ */
+ abstract class TermNameExtractor {
+ def apply(s: String): TermName
+ def unapply(name: TermName): Option[String]
+ }
+
+ /** The constructor/extractor for `TypeName` instances.
+ * @group Extractors
+ */
+ val TypeName: TypeNameExtractor
+
+ /** An extractor class to create and pattern match with syntax `TypeName(s)`.
+ * @group Extractors
+ */
+ abstract class TypeNameExtractor {
+ def apply(s: String): TypeName
+ def unapply(name: TypeName): Option[String]
+ }
}
diff --git a/src/reflect/scala/reflect/api/Trees.scala b/src/reflect/scala/reflect/api/Trees.scala
index cfa6315797..34be977905 100644
--- a/src/reflect/scala/reflect/api/Trees.scala
+++ b/src/reflect/scala/reflect/api/Trees.scala
@@ -3018,15 +3018,19 @@ trait Trees { self: Universe =>
/** The constructor/extractor for `Modifiers` instances.
* @group Traversal
*/
- val Modifiers: ModifiersCreator
+ val Modifiers: ModifiersExtractor
+
+ @deprecated("Use ModifiersExtractor instead", "2.11.0")
+ type ModifiersCreator = ModifiersExtractor
/** An extractor class to create and pattern match with syntax `Modifiers(flags, privateWithin, annotations)`.
* Modifiers encapsulate flags, visibility annotations and Scala annotations for member definitions.
* @group Traversal
*/
- abstract class ModifiersCreator {
+ abstract class ModifiersExtractor {
def apply(): Modifiers = Modifiers(NoFlags, tpnme.EMPTY, List())
def apply(flags: FlagSet, privateWithin: Name, annotations: List[Tree]): Modifiers
+ def unapply(mods: Modifiers): Option[(FlagSet, Name, List[Tree])]
}
/** The factory for `Modifiers` instances.
diff --git a/src/reflect/scala/reflect/internal/Names.scala b/src/reflect/scala/reflect/internal/Names.scala
index cea9215ae2..b60d1e619f 100644
--- a/src/reflect/scala/reflect/internal/Names.scala
+++ b/src/reflect/scala/reflect/internal/Names.scala
@@ -463,6 +463,11 @@ trait Names extends api.Names {
implicit val TermNameTag = ClassTag[TermName](classOf[TermName])
+ object TermName extends TermNameExtractor {
+ def apply(s: String) = newTermName(s)
+ def unapply(name: TermName): Option[String] = Some(name.toString)
+ }
+
sealed abstract class TypeName(index0: Int, len0: Int, hash: Int) extends Name(index0, len0) {
type ThisNameType = TypeName
protected[this] def thisName: TypeName = this
@@ -492,4 +497,9 @@ trait Names extends api.Names {
}
implicit val TypeNameTag = ClassTag[TypeName](classOf[TypeName])
+
+ object TypeName extends TypeNameExtractor {
+ def apply(s: String) = newTypeName(s)
+ def unapply(name: TypeName): Option[String] = Some(name.toString)
+ }
}
diff --git a/src/reflect/scala/reflect/internal/Trees.scala b/src/reflect/scala/reflect/internal/Trees.scala
index 9e737528d2..9795299342 100644
--- a/src/reflect/scala/reflect/internal/Trees.scala
+++ b/src/reflect/scala/reflect/internal/Trees.scala
@@ -932,7 +932,7 @@ trait Trees extends api.Trees { self: SymbolTable =>
override def toString = "Modifiers(%s, %s, %s)".format(flagString, annotations mkString ", ", positions)
}
- object Modifiers extends ModifiersCreator
+ object Modifiers extends ModifiersExtractor
implicit val ModifiersTag = ClassTag[Modifiers](classOf[Modifiers])
diff --git a/test/files/scalacheck/ReflectionExtractors.scala b/test/files/scalacheck/ReflectionExtractors.scala
new file mode 100644
index 0000000000..a2615feb3e
--- /dev/null
+++ b/test/files/scalacheck/ReflectionExtractors.scala
@@ -0,0 +1,52 @@
+import org.scalacheck._
+import Prop._
+import Gen._
+import Arbitrary._
+
+import scala.reflect.runtime.universe._
+import Flag._
+
+object Test extends Properties("reflection extractors") {
+
+ val genFlag = oneOf(
+ TRAIT, INTERFACE, MUTABLE, MACRO, DEFERRED, ABSTRACT, FINAL, SEALED,
+ IMPLICIT, LAZY, OVERRIDE, PRIVATE, PROTECTED, LOCAL, CASE, ABSOVERRIDE,
+ BYNAMEPARAM, PARAM, COVARIANT, CONTRAVARIANT, DEFAULTPARAM, PRESUPER,
+ DEFAULTINIT
+ )
+ val genModifiers =
+ for(flag <- genFlag; privateWithin <- genName)
+ yield Modifiers(flag, privateWithin, Nil)
+ val genTermName = for(name <- arbitrary[String]) yield TermName(name)
+ val genTypeName = for(name <- arbitrary[String]) yield TypeName(name)
+ val genName = oneOf(genTermName, genTypeName)
+
+ implicit val arbTermName: Arbitrary[TermName] = Arbitrary(genTermName)
+ implicit val arbTypeName: Arbitrary[TypeName] = Arbitrary(genTypeName)
+ implicit val arbName: Arbitrary[Name] = Arbitrary(genName)
+ implicit val arbMods: Arbitrary[Modifiers] = Arbitrary(genModifiers)
+
+ property("extract term name") = forAll { (name: TermName) =>
+ val TermName(s) = name
+ s == name.toString
+ }
+
+ property("extract type name") = forAll { (name: TypeName) =>
+ val TypeName(s) = name
+ s == name.toString
+ }
+
+ property("extract term or type name") = forAll { (name: Name) =>
+ name match {
+ case TermName(s) => s == name.toString
+ case TypeName(s) => s == name.toString
+ }
+ }
+
+ property("extract modifiers") = forAll { (mods: Modifiers) =>
+ val Modifiers(flags, priv, annots) = mods
+ flags == mods.flags &&
+ priv == mods.privateWithin &&
+ annots == mods.annotations
+ }
+} \ No newline at end of file