@@ -689,6 +689,50 @@ private def sumExpr(args1: Seq[Expr[Int]])(given QuoteContext): Expr[Int] = {
689689}
690690```
691691
692+ #### Recovering precise types using patterns
693+
694+ Sometimes it is necessary to get a more precise type for an expression. This can be achived using the following pattern match.
695+
696+ ``` scala
697+ def f (exp : Expr [Any ]) =
698+ expr match
699+ case ' { $x : $t } =>
700+ // If the pattern match succeeds, then there is some type `T` such that
701+ // - `x` is bound to a variable of type `Expr[T]`
702+ // - `t` is bound to a given instance of type `Type[T]`
703+ // That is, we have `x: Expr[T]` and `given t: Type[T]`, for some (unknown) type `T`.
704+ ```
705+
706+ This might be used to then perform an implicit search as in:
707+
708+
709+ ``` scala
710+ inline def (sc : StringContext ) showMe(args : => Any * ): String = $ { showMeExpr(' sc , ' args ) }
711+
712+ private def showMeExpr (sc : Expr [StringContext ], argsExpr : Expr [Seq [Any ]])(given qctx : QuoteContext ): Expr [String ] = {
713+ argsExpr match {
714+ case ExprSeq (argExprs) =>
715+ val argShowedExprs = argExprs.map {
716+ case ' { $arg : $tp } =>
717+ val showTp = ' [Show [$tp]]
718+ summonExpr(given showTp )) match {
719+ case Some (showExpr) => ' { $showExpr.show($arg) }
720+ case None => qctx.error(s " could not find implicit for ${showTp.show}" , arg); ' {??? }
721+ }
722+ }
723+ val newArgsExpr = Expr .ofSeq(argShowedExprs)
724+ ' { $sc.s($newArgsExpr : _* ) }
725+ case _ =>
726+ // `new StringContext(...).showMeExpr(args: _*)` not an explicit `showMeExpr"..."`
727+ qctx.error(s " Args must be explicit " , argsExpr)
728+ ' {??? }
729+ }
730+ }
731+
732+ trait Show [- T ] {
733+ def show (x : T ): String
734+ }
735+ ```
692736
693737### More details
694738[ More details] ( ./macros-spec.md )
0 commit comments