diff --git a/docs/docs/reference/changed-features/numeric-literals.md b/docs/docs/reference/changed-features/numeric-literals.md index 813649f68790..86f736320c5d 100644 --- a/docs/docs/reference/changed-features/numeric-literals.md +++ b/docs/docs/reference/changed-features/numeric-literals.md @@ -178,7 +178,7 @@ BigFloat.FromDigits.fromDigits("1e100000000000") ``` Evaluating this expression throws a `NumberTooLarge` exception at run time. We would like it to produce a compile-time error instead. We can achieve this by tweaking the `BigFloat` class -with a small dose of meta-programming. The idea is to turn the `fromDigits` method +with a small dose of metaprogramming. The idea is to turn the `fromDigits` method into a macro, i.e. make it an inline method with a splice as right hand side. To do this, replace the `FromDigits` instance in the `BigFloat` object by the following two definitions: ```scala diff --git a/docs/docs/reference/features-classification.md b/docs/docs/reference/features-classification.md index 5598f001f709..1b74cde065c9 100644 --- a/docs/docs/reference/features-classification.md +++ b/docs/docs/reference/features-classification.md @@ -5,7 +5,7 @@ date: April 6, 2019 author: Martin Odersky --- -This document provides an overview of the constructs proposed for Scala 3 with the aim to facilitate the discussion what to include and when to include it. It classifies features into eight groups: (1) essential foundations, (2) simplifications, (3) restrictions, (4) dropped features, (5) changed features, (6) new features, (7) features oriented towards meta-programming with the aim to replace existing macros, and (8) changes to type checking and inference. +This document provides an overview of the constructs proposed for Scala 3 with the aim to facilitate the discussion what to include and when to include it. It classifies features into eight groups: (1) essential foundations, (2) simplifications, (3) restrictions, (4) dropped features, (5) changed features, (6) new features, (7) features oriented towards metaprogramming with the aim to replace existing macros, and (8) changes to type checking and inference. Each group contains sections classifying the status (i.e. relative importance to be a part of Scala 3, and relative urgency when to decide this) and the migration cost of the constructs in it. @@ -160,13 +160,13 @@ Enums offer an essential simplification of fundamental use patterns, so they sho Being new features, existing code migrates without changes. To be sure, sometimes it would be attractive to rewrite code to make use of the new features in order to increase clarity and conciseness. -## Meta Programming +## Metaprogramming -The following constructs together aim to put meta programming in Scala on a new basis. So far, meta programming was achieved by a combination of macros and libraries such as Shapeless that were in turn based on some key macros. Current Scala 2 macro mechanisms are a thin veneer on top the current Scala 2 compiler, which makes them fragile and in many cases impossible to port to Scala 3. +The following constructs together aim to put metaprogramming in Scala on a new basis. So far, metaprogramming was achieved by a combination of macros and libraries such as Shapeless that were in turn based on some key macros. Current Scala 2 macro mechanisms are a thin veneer on top the current Scala 2 compiler, which makes them fragile and in many cases impossible to port to Scala 3. It's worth noting that macros were never included in the Scala 2 language specification and were so far made available only under an `-experimental` flag. This has not prevented their widespread usage. -To enable porting most uses of macros, we are experimenting with the advanced language constructs listed below. These designs are more provisional than the rest of the proposed language constructs for Scala 3.0. There might still be some changes until the final release. Stabilizing the feature set needed for meta programming is our first priority. +To enable porting most uses of macros, we are experimenting with the advanced language constructs listed below. These designs are more provisional than the rest of the proposed language constructs for Scala 3.0. There might still be some changes until the final release. Stabilizing the feature set needed for metaprogramming is our first priority. - [Match Types](new-types/match-types.md) allow computation on types. - [Inline](metaprogramming/inline.md) provides diff --git a/docs/docs/reference/metaprogramming/macros-spec.md b/docs/docs/reference/metaprogramming/macros-spec.md index a2ccd0de45ff..9129bd00b5fe 100644 --- a/docs/docs/reference/metaprogramming/macros-spec.md +++ b/docs/docs/reference/metaprogramming/macros-spec.md @@ -161,7 +161,7 @@ is studied [separately](./simple-smp.md). ## Going Further -The meta-programming framework as presented and currently implemented is quite restrictive +The metaprogramming framework as presented and currently implemented is quite restrictive in that it does not allow for the inspection of quoted expressions and types. It’s possible to work around this by providing all necessary information as normal, unquoted inline parameters. But we would gain @@ -234,7 +234,7 @@ envisage a solution that allows the former but not the latter. ## Conclusion -Meta-programming has a reputation of being difficult and confusing. +Metaprogramming has a reputation of being difficult and confusing. But with explicit `Expr/Type` types and quotes and splices it can become downright pleasant. A simple strategy first defines the underlying quoted or unquoted values using `Expr` and `Type` and then inserts quotes and splices to make the types diff --git a/docs/docs/reference/metaprogramming/macros.md b/docs/docs/reference/metaprogramming/macros.md index 033396d4704d..8a918bf70a48 100644 --- a/docs/docs/reference/metaprogramming/macros.md +++ b/docs/docs/reference/metaprogramming/macros.md @@ -126,7 +126,7 @@ that program elaboration will lead to neither of the two unwanted situations described above. In what concerns the range of features it covers, this form of macros introduces -a principled meta programming framework that is quite close to the MetaML family of +a principled metaprogramming framework that is quite close to the MetaML family of languages. One difference is that MetaML does not have an equivalent of the PCP - quoted code in MetaML _can_ access variables in its immediately enclosing environment, with some restrictions and caveats since such accesses involve @@ -362,8 +362,8 @@ is handled by the compiler, using the algorithm sketched above. ### Relationship with Inline -Seen by itself, principled meta-programming looks more like a framework for -runtime metaprogramming than one for compile-time meta programming with macros. +Seen by itself, principled metaprogramming looks more like a framework for +runtime metaprogramming than one for compile-time metaprogramming with macros. But combined with Dotty’s `inline` feature it can be turned into a compile-time system. The idea is that macro elaboration can be understood as a combination of a macro library and a quoted program. For instance, here’s the `assert` macro @@ -375,8 +375,8 @@ object Macros { inline def assert(inline expr: Boolean): Unit = ${ assertImpl('expr) } - def assertImpl(expr: Expr[Boolean]) = - '{ if !($expr) then throw new AssertionError("failed assertion: " + ${expr.show}) } + def assertImpl(expr: Expr[Boolean])(using QuoteContext) = + '{ if !($expr) then throw new AssertionError("failed assertion: " + ${expr.show}) } // autolift is applied } object App { @@ -502,7 +502,7 @@ function `f` and one `sum` that performs a sum by delegating to `map`. ```scala object Macros { - def map[T](arr: Expr[Array[T]], f: Expr[T] => Expr[Unit])(implicit t: Type[T]): Expr[Unit] = '{ + def map[T](arr: Expr[Array[T]], f: Expr[T] => Expr[Unit])(using t: Type[T], qctx: QuoteContext): Expr[Unit] = '{ var i: Int = 0 while (i < ($arr).length) { val element: $t = ($arr)(i) @@ -511,7 +511,7 @@ object Macros { } } - def sum(arr: Expr[Array[Int]]): Expr[Int] = '{ + def sum(arr: Expr[Array[Int]])(using QuoteContext): Expr[Int] = '{ var sum = 0 ${ map(arr, x => '{sum += $x}) } sum @@ -719,7 +719,7 @@ This might be used to then perform an implicit search as in: ```scala inline def (inline sc: StringContext).showMe(inline args: Any*): String = ${ showMeExpr('sc, 'args) } -private def showMeExpr(sc: Expr[StringContext], argsExpr: Expr[Seq[Any]])(using qctx: QuoteContext): Expr[String] = { +private def showMeExpr(sc: Expr[StringContext], argsExpr: Expr[Seq[Any]])(using QuoteContext): Expr[String] = { argsExpr match { case Varargs(argExprs) => val argShowedExprs = argExprs.map { @@ -765,7 +765,7 @@ the subxpression of type `Expr[Int]` is bound to `body` as an `Expr[Int => Int]` ```scala inline def eval(inline e: Int): Int = ${ evalExpr('e) } -private def evalExpr(using QuoteContext)(e: Expr[Int]): Expr[Int] = { +private def evalExpr(e: Expr[Int])(using QuoteContext): Expr[Int] = { e match { case '{ val y: Int = $x; $body(y): Int } => // body: Expr[Int => Int] where the argument represents references to y diff --git a/docs/docs/reference/metaprogramming/simple-smp.md b/docs/docs/reference/metaprogramming/simple-smp.md index c968cd714213..ec5709ed8f45 100644 --- a/docs/docs/reference/metaprogramming/simple-smp.md +++ b/docs/docs/reference/metaprogramming/simple-smp.md @@ -1,10 +1,10 @@ --- layout: doc-page -title: "The Meta-theory of Symmetric Meta-programming" +title: "The Meta-theory of Symmetric Metaprogramming" --- This note presents a simplified variant of -[principled meta-programming](./macros.md) +[principled metaprogramming](./macros.md) and sketches its soundness proof. The variant treats only dialogues between two stages. A program can have quotes which can contain splices (which can contain quotes, which can contain splices, and so diff --git a/docs/docs/reference/metaprogramming/staging.md b/docs/docs/reference/metaprogramming/staging.md index c2c6e0bc984a..1a64d698093c 100644 --- a/docs/docs/reference/metaprogramming/staging.md +++ b/docs/docs/reference/metaprogramming/staging.md @@ -3,8 +3,8 @@ layout: doc-page title: "Multi-Stage Programming" --- -The framework expresses at the same time compile-time meta-programming and -multi-stage programming. We can think of compile-time meta-programming as a +The framework expresses at the same time compile-time metaprogramming and +multi-stage programming. We can think of compile-time metaprogramming as a two stage compilation process: one that we write the code in top-level splices, that will be used for code generation (macros) and one that will perform all necessary evaluations at compile-time and an object program that we will run diff --git a/docs/docs/reference/overview.md b/docs/docs/reference/overview.md index fd843b059892..7ab8705dd179 100644 --- a/docs/docs/reference/overview.md +++ b/docs/docs/reference/overview.md @@ -15,7 +15,7 @@ The language redesign was guided by three main goals: - Further improve the consistency and expressiveness of Scala's language constructs. Corresponding to these goals, the language changes fall into seven categories: -(1) Core constructs to strengthen foundations, (2) simplifications and (3) restrictions, to make the language easier and safer to use, (4) dropped constructs to make the language smaller and more regular, (5) changed constructs to remove warts, and increase consistency and usability, (6) new constructs to fill gaps and increase expressiveness, (7) a new, principled approach to meta-programming that replaces today's experimental macros. +(1) Core constructs to strengthen foundations, (2) simplifications and (3) restrictions, to make the language easier and safer to use, (4) dropped constructs to make the language smaller and more regular, (5) changed constructs to remove warts, and increase consistency and usability, (6) new constructs to fill gaps and increase expressiveness, (7) a new, principled approach to metaprogramming that replaces today's experimental macros. ## Essential Foundations @@ -110,13 +110,13 @@ These are additions to the language that make it more powerful or pleasant to us - [Polymorphic Function Types](https://github.com/lampepfl/dotty/pull/4672) generalize polymorphic methods to dependent function values and types. _Current status_: There is a proposal, and a prototype implementation, but the implementation has not been finalized or merged yet. - [Kind Polymorphism](other-new-features/kind-polymorphism.md) allows the definition of operators working equally on types and type constructors. -## Meta Programming +## Metaprogramming -The following constructs together aim to put meta programming in Scala on a new basis. So far, meta programming was achieved by a combination of macros and libraries such as Shapeless that were in turn based on some key macros. Current Scala 2 macro mechanisms are a thin veneer on top the current Scala 2 compiler, which makes them fragile and in many cases impossible to port to Scala 3. +The following constructs together aim to put metaprogramming in Scala on a new basis. So far, metaprogramming was achieved by a combination of macros and libraries such as Shapeless that were in turn based on some key macros. Current Scala 2 macro mechanisms are a thin veneer on top the current Scala 2 compiler, which makes them fragile and in many cases impossible to port to Scala 3. It's worth noting that macros were never included in the Scala 2 language specification and were so far made available only under an `-experimental` flag. This has not prevented their widespread usage. -To enable porting most uses of macros, we are experimenting with the advanced language constructs listed below. These designs are more provisional than the rest of the proposed language constructs for Scala 3.0. There might still be some changes until the final release. Stabilizing the feature set needed for meta programming is our first priority. +To enable porting most uses of macros, we are experimenting with the advanced language constructs listed below. These designs are more provisional than the rest of the proposed language constructs for Scala 3.0. There might still be some changes until the final release. Stabilizing the feature set needed for metaprogramming is our first priority. - [Match Types](new-types/match-types.md) allow computation on types. - [Inline](metaprogramming/inline.md) provides diff --git a/library/src-bootstrapped/scala/quoted/QuoteContext.scala b/library/src-bootstrapped/scala/quoted/QuoteContext.scala index 7ec7a0d9442f..b87f6d5d3c74 100644 --- a/library/src-bootstrapped/scala/quoted/QuoteContext.scala +++ b/library/src-bootstrapped/scala/quoted/QuoteContext.scala @@ -5,14 +5,14 @@ import scala.quoted.show.SyntaxHighlight /** Quotation context provided by a macro expansion or in the scope of `scala.quoted.run`. * Used to perform all operations on quoted `Expr` or `Type`. * - * It contains the low-level Typed AST API `tasty` meta-programming API. + * It contains the low-level Typed AST API `tasty` metaprogramming API. * This API does not have the static type guarantiees that `Expr` and `Type` provide. * * @param tasty Typed AST API. Usage: `def f(qctx: QuoteContext) = { import qctx.tasty._; ... }`. */ trait QuoteContext { self => - /** Low-level Typed AST API `tasty` meta-programming API. + /** Low-level Typed AST API `tasty` metaprogramming API. * This API does not have the static type guarantiees that `Expr` and `Type` provide. */ val tasty: scala.tasty.Reflection