Skip to content

Commit

Permalink
Removed leaky abstraction with isCaseObject passed into fulfillAsPatt…
Browse files Browse the repository at this point in the history
…ernMatchCase
  • Loading branch information
MateuszKubuszok committed Apr 4, 2024
1 parent 6f4390a commit c7f4283
Show file tree
Hide file tree
Showing 4 changed files with 13 additions and 20 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@ private[compiletime] trait ExprPromisesPlatform extends ExprPromises { this: Def
protected object PatternMatchCase extends PatternMatchCaseModule {

def matchOn[From: Type, To: Type](src: Expr[From], cases: List[PatternMatchCase[To]]): Expr[To] = {
val casesTrees = cases.map { case PatternMatchCase(someFrom, usage, fromName, _) =>
val casesTrees = cases.map { case PatternMatchCase(someFrom, usage, fromName) =>
import someFrom.Underlying as SomeFrom
val markUsed = Expr.suppressUnused(c.Expr[someFrom.Underlying](q"$fromName"))
cq"""$fromName : $SomeFrom => { $markUsed; $usage }"""
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -100,7 +100,7 @@ private[compiletime] trait ExprPromisesPlatform extends ExprPromises { this: Def

def matchOn[From: Type, To: Type](src: Expr[From], cases: List[PatternMatchCase[To]]): Expr[To] = Match(
'{ ${ src.asTerm.changeOwner(Symbol.spliceOwner).asExprOf[From] }: @scala.unchecked }.asTerm,
cases.map { case PatternMatchCase(someFrom, usage, fromName, isCaseObject) =>
cases.map { case PatternMatchCase(someFrom, usage, fromName) =>
import someFrom.Underlying as SomeFrom
// Unfortunately, we cannot do
// case $fromName: $SomeFrom => $using
Expand All @@ -126,7 +126,7 @@ private[compiletime] trait ExprPromisesPlatform extends ExprPromises { this: Def
// Scala 3's enums' parameterless cases are vals with type erased, so w have to match them by value
// case arg @ Enum.Value => ...
CaseDef(Bind(bindName, Ident(TypeRepr.of[someFrom.Underlying].typeSymbol.termRef)), None, body)
else if isCaseObject then
else if TypeRepr.of[someFrom.Underlying].typeSymbol.flags.is(Flags.Module) then
// case objects are also matched by value but the tree for them is generated in a slightly different way
// case arg @ Enum.Value => ...
CaseDef(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -47,12 +47,11 @@ private[compiletime] trait ExprPromises { this: Definitions =>
): Expr[(From, From2) => To] =
ExprPromise.createLambda2(fromName, promise.fromName, combine(usage, promise.usage))

def fulfillAsPatternMatchCase[To](isCaseObject: Boolean)(implicit ev: A <:< Expr[To]): PatternMatchCase[To] =
def fulfillAsPatternMatchCase[To](implicit ev: A <:< Expr[To]): PatternMatchCase[To] =
new PatternMatchCase(
someFrom = ExistentialType(Type[From]),
someFrom = Type[From].as_??,
usage = ev(usage),
fromName = fromName,
isCaseObject = isCaseObject
fromName = fromName
)

def partition[L, R](implicit
Expand Down Expand Up @@ -218,18 +217,13 @@ private[compiletime] trait ExprPromises { this: Definitions =>
final protected class PatternMatchCase[To](
val someFrom: ??,
val usage: Expr[To],
val fromName: ExprPromiseName,
val isCaseObject: Boolean
val fromName: ExprPromiseName
)
protected val PatternMatchCase: PatternMatchCaseModule
protected trait PatternMatchCaseModule { this: PatternMatchCase.type =>

final def unapply[To](
patternMatchCase: PatternMatchCase[To]
): Some[(??, Expr[To], ExprPromiseName, Boolean)] =
Some(
(patternMatchCase.someFrom, patternMatchCase.usage, patternMatchCase.fromName, patternMatchCase.isCaseObject)
)
final def unapply[To](patternMatchCase: PatternMatchCase[To]): Some[(??, Expr[To], ExprPromiseName)] =
Some((patternMatchCase.someFrom, patternMatchCase.usage, patternMatchCase.fromName))

def matchOn[From: Type, To: Type](src: Expr[From], cases: List[PatternMatchCase[To]]): Expr[To]
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -172,8 +172,8 @@ private[compiletime] trait TransformSealedHierarchyToSealedHierarchyRuleModule {
// 2 or more matches - ambiguous coproduct instances
case toSubtypes =>
DerivationResult.ambiguousSubtypeTargets[From, To, Existential[ExprPromise[*, TransformationExpr[To]]]](
ExistentialType(fromSubtype.Underlying),
toSubtypes.map(to => ExistentialType(to.Underlying))
fromSubtype.Underlying.as_??,
toSubtypes.map(to => to.Underlying.as_??)
)
}
}
Expand Down Expand Up @@ -216,7 +216,7 @@ private[compiletime] trait TransformSealedHierarchyToSealedHierarchyRuleModule {
subtypeMappings
.map { subtype =>
subtype.value.ensurePartial
.fulfillAsPatternMatchCase[partial.Result[To]](isCaseObject = subtype.Underlying.isCaseObject)
.fulfillAsPatternMatchCase[partial.Result[To]]
}
.matchOn(ctx.src)
)
Expand All @@ -225,8 +225,7 @@ private[compiletime] trait TransformSealedHierarchyToSealedHierarchyRuleModule {
DerivationResult.expandedTotal(
subtypeMappings
.map { subtype =>
subtype.value.ensureTotal
.fulfillAsPatternMatchCase[To](isCaseObject = subtype.Underlying.isCaseObject)
subtype.value.ensureTotal.fulfillAsPatternMatchCase[To]
}
.matchOn(ctx.src)
)
Expand Down

0 comments on commit c7f4283

Please sign in to comment.