-
Notifications
You must be signed in to change notification settings - Fork 1.1k
Decouple quoted Type interface from encoding #9485
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Decouple quoted Type interface from encoding #9485
Conversation
Before, `quoted.Type` was defined as ```scala // old class Type[X <: AnyKind]: type T = X ``` Where `T` is the proper type of the instance of a `Type`. This is the type used for all operations within the compiler. The only purpose of the type `X` was to be able to write context bounds as `[X: Type]` and staged types `Type[X]` instead of `Type { type T = X }`. Unfortunately, the type `X` makes the assumption that `X` is known, which implies that instances of `Type` with unknown types need to be encoded with a whildcard type. A `val t: Type[?] = ...` is unusable as we cannot heal staged wildcard types, even though we do have a `t.T` which can be handled. Now, we change the definition of `Type` to only have the type member. ```scala // new class Type: type T <: AnyKind ``` This solves the aforementioned limitations with unkown staged types. Now we are also able to remove the wildcard from `QuoteContext.tasty.Type.seal` and the result can be used in quotes. To keep the context bound syntax and provide more descriptive name for the concept, we defined the `quoted.Staged` type alias. ```scala type Staged[X <: AnyKind] = Type { type T = X } ```
fa59dd9
to
d488d31
Compare
@liufengyun could you have a look at this PR? Only the community build fails, I will update it once we settled on the design/names. |
I propose to name this |
Could you produce a simple example where the current scheme does not work, and how it works after the change? |
For example when we // Current
import scala.quoted._
def f(using t: Type[? <: Any])(using QuoteContext): Unit = '{
(x: $t) => ???
// | ^
// | Cannot splice t.T because it is a wildcard type
} // With this PR
import scala.quoted._
def f1(using t: Staged[? <: Any])(using QuoteContext): Unit = '{
(x: $t) => ??? // ok
}
// or the equivalent
def f2(using t: Type { type T <: Any } )(using QuoteContext): Unit = '{
(x: $t) => ??? // ok
} Note: there is an orthogonal improvement that can be done to avoid the extra |
We are exposing a new concept BTW, technically it seems we are trying to find an encoding for the absence of existential types. trait SomeType[U] {
type T <: U
val T: Type[T]
}
def f1(t: SomeType[U])(using QuoteContext): Unit = '{
(x: ${t.T}) => ??? // ok
} |
Or, even simpler, what about changing the type signature of def seal[T]: Expr[T] = ... Is it enough for use cases that this PR tries to support? |
The On the other side I want to avoid using |
Another argument to avoid |
@liufengyun, not sure what this means: def seal[T]: Expr[T] = ... Maybe you meant def seal[T]: Type[T] = ... if so, this does not work because we do not have the type |
Yes, I mean exactly that. I'm wondering why we need the existential I feel |
But |
0e27489
to
57cc41a
Compare
57cc41a
to
d488d31
Compare
Before,
quoted.Type
was defined asWhere
T
is the proper type of the instance of aType
. This is the type used for all operations within the compiler.The only purpose of the type
X
was to be able to write context bounds as[X: Type]
and staged typesType[X]
instead ofType { type T = X }
.Unfortunately, the type
X
makes the assumption thatX
is known, which implies that instances ofType
with unknown types need to be encoded with a whildcard type.A
val t: Type[?] = ...
is unusable as we cannot heal staged wildcard types, even though we do have at.T
which can be handled.Now, we change the definition of
Type
to only have the type member.This solves the aforementioned limitations with unkown staged types.
Now we are also able to remove the wildcard from
QuoteContext.tasty.Type.seal
and the result can be used in quotes.To keep the context bound syntax and provide more descriptive name for the concept, we defined the
quoted.Staged
type alias.