Pattern matching on opaque type unions #16449
-
Hi there 👋 I've placed this question under "Metaprogramming" but feel free to change it if my question is not really suitable for this. My understanding is that the outer type for opaque types is erased during compiling, which means we can't check the outer type during runtime. This means that if we have a union of 2 opaque types which have the same underlying type, using pattern matching to differentiate them during runtime is not possible. As an example: object opaques:
opaque type Foo = String
opaque type Bar = String
type FooBar = Foo | Bar
val foo: Foo = "foo"
val bar: Bar = "foo"
end opaques
object program:
import opaques.*
def handleFooBar(fooBar: FooBar): Unit = fooBar match
case _: Foo => throw new Throwable("foo")
case _: Bar => println("bar")
@main def main =
handleFooBar(bar)
end program In this case inline def handleFooBar(inline fooBar: FooBar): Unit = inline fooBar match
case _: Foo => throw new Throwable("foo")
case _: Bar => println("bar") However, this might not always be possible to do, particularly in cases where we have other non-inlined methods in the middle. I was wondering, is there any other way that this can be achieved or is inlining the only solution? |
Beta Was this translation helpful? Give feedback.
Replies: 1 comment 1 reply
-
if you have some kind of runtime inspectable property that distinguishes |
Beta Was this translation helpful? Give feedback.
if you have some kind of runtime inspectable property that distinguishes
Foo
andBar
then you can define a givenscala.reflect.TypeTest
instance for them - see API Docs and Scala 3 Reference. However it appears in your example thatfoo: Foo
andbar: Bar
both== "foo"
, so there is no way to distinguish them in this case