> On May 8, 2018, at 7:16 PM, Brian Goetz <[email protected]> wrote:
> 
>> I am concerned about the treatment of 'break' statements in switch 
>> expressions. The following seems like something that would be very natural 
>> to do:
>> 
>> boolean x = switch (expr()) {
>>   case FOO -> {
>>       for (String s : strings) {
>>           if (s.isEmpty()) break false;
>>       }
>>       break true;
>>   }
>>   case BAR -> true;
>>   default -> false;
>> };
> 
> This should be valid.  If you recall the table I posted regarding abrupt 
> completion, the for-loop should be transparent to “break val”, in the same 
> way it is transparent to “return” or “throw” or that block expressions are 
> transparent to all abruptly completing statements.  The constraint on “case 
> Foo -> { … }” is that the block must complete abruptly via break-value.  

Definitely prohibited in the current spec. But... this table?

> More formally; we can construct a table whose rows are the control constructs 
> and whose columns are the nonlocal branches, and whose entries are "handlers" 
> for a nonlocal branch.  Each block has a parent (the immediately enclosing 
> block.)
> 
>             break-e   break   break-l   continue   return
> 
> switch-e      L         X       X         X          X
> switch-s      X         L       P         L          P
> for           X         L       P         L          P
> while         X         L       P         L          P
> block         P         P       P         P          P
> labeled       X         X L*        X          P
> lambda        X         X       X         X L
> method        X         X X         X          L
> 
> The handlers mean:
> 
> X -- not allowed
> P -- let the parent handle it
> L -- handle it and complete normally
> L* -- handle it and complete normally if the labels match, otherwise P
> 

I'm worried about those X's in the first column.

A simplified model which the spec suggests: there are certain constructs that 
introduce control flow barriers: method, constructor, initializer, lambda body, 
switch expression body. It's an error if a break/continue/return reaches one of 
those and cannot be handled. Nested within one of those, all constructs may 
choose to handle a break/continue/return, or (by default) propagate it outward.

A method/constructor/initializer/lambda body/switch expression body cannot 
choose to propagate a break/continue/return outward (i.e., "P" is not valid), 
and other constructs cannot choose to prohibit a break/continue/return (i.e., 
"X" is not valid).

Reply via email to