scala / scala3

The Scala 3 compiler, also known as Dotty.
https://dotty.epfl.ch
Apache License 2.0
5.83k stars 1.05k forks source link

Can't patmat to extract type constructor from quoted type #11738

Closed japgolly closed 1 year ago

japgolly commented 3 years ago

Using 3.0.0-RC1, I'm trying to test whether a type is in the shape of F[A].

import scala.quoted.*

def blah[A](using Quotes, Type[A]): Expr[Unit] =
  Type.of[A] match
    case '[h *: t] => println(s"h = ${Type.show[h]}, t = ${Type.show[t]}") // ok
    case '[f[a]]   => println(s"f = ${Type.show[f]}, a = ${Type.show[a]}") // error
    case _         =>
  '{()}

The tuple case works, no problem. The f[a] case doesn't compile and instead fails with:

[error] -- [E053] Type Error: /home/golly/projects/public/univeq/univeq/shared/src/main/scala-3/japgolly/univeq/internal/test.scala:6:11 
[error] 6 |    case '[f[a]]   => println(s"f = ${Type.show[f]}, a = ${Type.show[a]}")
[error]   |           ^^^^
[error]   |           f$given1.Underlying does not take type parameters

[error] -- [E006] Not Found Error: /home/golly/projects/public/univeq/univeq/shared/src/main/scala-3/japgolly/univeq/internal/test.scala:6:69 
[error] 6 |    case '[f[a]]   => println(s"f = ${Type.show[f]}, a = ${Type.show[a]}")
[error]   |                                                                     ^
[error]   |                                                         Not found: type a
japgolly commented 3 years ago

Hey @nicolasstucki , would you happen to know an alternative way of doing this? I'm a bit stuck looking for a workaround :(

japgolly commented 3 years ago

Found workaround thanks to @smarter : use TypeRepr.of to get to tasty

nicolasstucki commented 3 years ago

The root of the issue is that we have no way to infer or tell the kind of the type variable.

The alternative is to use a pattern on expressions. I tried it but hit some bug or limitation. I need to dig into it. Nevertheless, the idea is to do

'{ ??? : A } match
  case '{ type f[X] ; ??? : `f`[t] } =>