This inclination (guards are simple, continue is complicated) is also
supported by the following observation: we just went through a big
exercise for (optimistic) totality, but any pattern that is guarded
(imperatively or declaratively) can't be assumed to cover anything. It
is far easier to spot a pattern with a guard (even if the guard is `&&
false`) and know it doesn't contribute to totality, than to scan the
imperative body looking for a `continue`.
On 8/26/2020 4:53 PM, Kevin Bourrillion wrote:
I think it will usually be easy for users to keep guards simple, by
just extracting out a method when they're not, and the aesthetics will
even motivate them to do that.
With `continue`, there might be any amount of complexity, even state
changes, in the statement group before the `continue` is hit, and it's
not necessarily extractable.
Really, it just seems like we now have two different kinds of
fall-through layered on top of each other. The silent continue is for
going to the next group, while the explicit continue goes back to
checking for a match. Why that way and not the other way around? Just
legacy reasons.
I like the guards.
On Fri, Aug 14, 2020 at 10:21 AM Brian Goetz <[email protected]
<mailto:[email protected]>> wrote:
- Guards. (John, Tagir) There is acknowledgement that some sort
of "whoops, not this case" support is needed in order to maintain
switch as a useful construct in the face of richer case labels,
but some disagreement about whether an imperative statement
(e.g., continue) or a declarative guard (e.g., `when
<predicate>`) is the right choice.
This is probably the biggest blocking decision in front of us.
John correctly points out that the need for some sort of guard is
a direct consequence of making switch stronger; with the current
meaning of switch, which is "which one of these is it", there's no
need for backtracking, but as we can express richer case labels,
the risk of the case label _not being rich enough_ starts to loom.
We explored rolling boolean guards into patterns themselves (`P &&
g`), which was theoretically attractive but turned out to not be
all that great. There are some potential ambiguities (even if we
do something else about constant patterns, there are still some
patterns that look like expressions and vice versa, making the
grammar ugly here) and it just doesn't have that much incremental
expressive power, since the most credible other use of patterns
already (instanceof) has no problem conjoining additional
conditions, because it's a boolean expression. So this is largely
about filling in the gaps of switch so that we don't have
fall-off-the-cliff behaviors.
There are two credible approaches here:
- An imperative statement (like `continue` or `next-case`), which
means "whoops, fell in the wrong bucket, please backtrack to the
dispatch";
- A declarative clause on the case label (like `when
<predicate>`) that qualifies whether the case is selected.
Most of the discussion so far has been on the axis of "continue is
lower-level, and therefore better suited to be a language
primitive" vs "the code that uses guards is easier to read and
reason about." Assuming we have to do one (and I think we do), we
have three choices (one, the other, or both.) I think we should
step away from the either/or mentality and try to shine a light on
what goes well, or badly, when we _don't_ have one or the other.
For example, with guards, we can express fine degrees of
refinement in the case labels:
case P & g1: ...
case P & g2: ...
case P & g3: ...
but without them, we can only have one `case P`:
case P:
if (g1) { ... }
else if (g2) { ... }
else if (g3) { ... }
My main fear of the without-guards branches is that it will be
prohibitively hard to understand what a switch is doing, because
the case arms will be full of imperative control-flow logic.
On the other hand, a valid concern when you have guards is that
there will be so much logic in the guard that you won't be able to
tell where the case label ends and where the arm begins.
--
Kevin Bourrillion | Java Librarian | Google, Inc. |[email protected]
<mailto:[email protected]>