You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
While working on rakudo/rakudo#3199 I stumbled upon a problem with role concretization. In a brief, there is no way to say detect that two concretizations of them same role are actually the same. For example:
role R0 { }
role R1 does R0 { }
role R2 does R0 { }
class C does R1 does R2 { }
In the above example R0 would be specialized twice for each consuming role producing two different concretizations. Why this is a problem?
Conceptually, this breaks the principle of flattening down roles. I.e. theoretically, C consumes R0 once. In practice, the implementation simulates flattening and does it pretty well. But transitive introspection of concretizations results in two different copies of concrete R0.
Stemming from 1, implementation of Roles, submethods, constructors, destructors. #103 is broken because there is no legal way to build valid list of consumed roles. I'll get back to why is it so later. For now what matters is that constructors/destructor would be called twice on R0 as well as any submethod when called with .+-family of operators.
Any user operations based on MRO with roles included would also suffer from double-processing of the same role.
While trying to find a solution I considered the following options.
sort based on ParametricRoleHOW type objects. Would work well for non-parameterized roles. But will fail if:
role R0[::T] { }
role R1 does R0[Int] { }
role R2 does R0[Str] { }
for the obvious reason that while R0[::T] is the common base, R0[Int] and R0[Str] are two completely different concretizations.
Yet, it is still required that R0[AClass] would be considered same concretization even if declared at different consuming roles.
specialization of a role must result in same concretized role irrelevant of where it's done but only de a function of its arguments. That's the most appropriate solution but it depends on:
existence of a global concretization registry
ability to match specialization parameters to existing concretizations
the above is only possible if specialization of a role records the capture on which it is based
This approach would result in some slowdown due to the need of recording and later matching of captures. The cost of this slowdown could be slightly eliminated by limiting the search to the parametric role being specialized and, possibly, by having a unique ID for each capture based on its parameters.
Since I currently still investigating, no solution is considered good enough to start working on it. Hopefully, there're other ideas as to handle this situation or advises on how to resolve the above mentioned problem in best possible manner.
The text was updated successfully, but these errors were encountered:
I tend to try the option 2 and implement table lookup for concretizations. If successful, this could speedup role specialization for existing concretizations. Though might add to the startup time due to the need of rebuilding the lookup table from a lookup list. Unfortunately, the latter couldn't be avoided due to the lack of cross-precomp persistent object IDs.
By looking deeper into the problem I realized that global caching of concretizations is not possible due to the need of resolving $?CLASS and ::?CLASS for a particular role consumption.
Under this circumstances flattening down concretizations has rather simple solution.
While working on rakudo/rakudo#3199 I stumbled upon a problem with role concretization. In a brief, there is no way to say detect that two concretizations of them same role are actually the same. For example:
In the above example R0 would be specialized twice for each consuming role producing two different concretizations. Why this is a problem?
CconsumesR0once. In practice, the implementation simulates flattening and does it pretty well. But transitive introspection of concretizations results in two different copies of concreteR0..+-family of operators.While trying to find a solution I considered the following options.
sort based on
ParametricRoleHOWtype objects. Would work well for non-parameterized roles. But will fail if:for the obvious reason that while
R0[::T]is the common base,R0[Int]andR0[Str]are two completely different concretizations.Yet, it is still required that
R0[AClass]would be considered same concretization even if declared at different consuming roles.specialization of a role must result in same concretized role irrelevant of where it's done but only de a function of its arguments. That's the most appropriate solution but it depends on:
This approach would result in some slowdown due to the need of recording and later matching of captures. The cost of this slowdown could be slightly eliminated by limiting the search to the parametric role being specialized and, possibly, by having a unique ID for each capture based on its parameters.
Since I currently still investigating, no solution is considered good enough to start working on it. Hopefully, there're other ideas as to handle this situation or advises on how to resolve the above mentioned problem in best possible manner.
The text was updated successfully, but these errors were encountered: