Record pattern and side effects
forax at univ-mlv.fr
forax at univ-mlv.fr
Thu Apr 21 09:28:45 UTC 2022
----- Original Message -----
> From: "Brian Goetz" <brian.goetz at oracle.com>
> To: "Remi Forax" <forax at univ-mlv.fr>
> Cc: "amber-spec-experts" <amber-spec-experts at openjdk.java.net>
> Sent: Sunday, April 17, 2022 4:58:26 PM
> Subject: Re: Record pattern and side effects
> Yes, this is something we have to get “on the record”.
>
> Record patterns are a special case of deconstruction patterns; in general, we
> will invoke the deconstructor (which is some sort of imperative code) as part
> of the match, which may have side-effects or throw exceptions. With records,
> we go right to the accessors, but its the same game, so I’ll just say “invoke
> the deconstructor” to describe both.
>
> While we can do what we can to discourage side-effects in deconstructors, they
> will happen. This raises all sorts of questions about what flexibility the
> compiler has.
>
> Q: if we have
>
> case Foo(Bar(String s)):
> case Foo(Bar(Integer i)):
>
> must we call the Foo and Bar deconstructors once, twice, or “dealer’s choice”?
> (I know you like the trick of factoring a common head, and this is a good
> trick, but it doesn’t answer the general question.)
>
> Q: To illustrate the limitations of the “common head” trick, if we have
>
> case Foo(P, Bar(String s)):
> case Foo(Q, Bar(String s)):
>
> can we factor a common “tail”, where we invoke Foo and Bar just once, and then
> use P and Q against the first binding?
>
> Q: What about reordering? If we have disjoint patterns, can we reorder:
>
> case Foo(Bar x):
> case TypeDisjointWithFoo t:
> case Foo(Baz x):
>
> into
>
> case Foo(Bar x):
> case Foo(Baz x):
> case TypeDisjointWithFoo t:
>
> and then fold the head, so we only invoke the Foo dtor once?
>
> Most of the papers about efficient pattern dispatch are relatively little help
> on this front, because the come with the assumption of purity /
> side-effect-freedom. But it seems obvious that if we were trying to optimize
> dispatch, our cost model would be something like arithmetic op << type test <<
> dtor invocation, and so we’d want to optimize for minimizing dtor invocations
> where we can.
yes !
>
> We’ve already asked one of the questions on side effects (though not sure we
> agreed on the answer): what if the dtor throws? The working story is that the
> exception is wrapped in a MatchException. (I know you don’t like this, but
> let’s not rehash the same arguments.)
Wrapping exceptions into a MatchException destroy any idea of refactoring from a cascade of if ... instanceof to a switch.
I think refactoring is a use case we should support.
Rémi
More information about the amber-spec-experts
mailing list