JDK-8300691 - final variables in for loop headers should accept updates

Maurizio Cimadamore maurizio.cimadamore at oracle.com
Mon Oct 21 15:16:35 UTC 2024


On 21/10/2024 16:08, Archie Cobbs wrote:
> On Mon, Oct 21, 2024 at 10:01 AM Maurizio Cimadamore 
> <maurizio.cimadamore at oracle.com> wrote:
>
>     On 21/10/2024 15:39, Archie Cobbs wrote:
>
>>     So no special treatment of loop induction variables is needed.
>
>     I’m not sure of that. I mean, I “can see” why you’d think that.
>     But in which scope does STEP belong? Yes, it belongs to the for
>     loop header - but it is executed /after/ the loop. And, in fact,
>     it can even refer to variables that would otherwise be DU outside
>     the loop body:
>
>     |void m() { int i; for (int j = 0 ; j < 10 ; j = j + i) { i = 1;
>     // if this is commented out, error! } } |
>
>     So I’m not sure it is a /strict/ generalization :-)
>
> Sorry for not being more precise... all that I am implying by 
> "generalization" is this:
>
>   * Let X be a program X that currently does not compile, but would
>     successfully compile under the proposal in JDK-8341785 (allow
>     capture of basic for() loop variables)
>   * Then X would also compile under the "final or effectively frozen
>     at the point of capture" proposal
>
> Proof: Let v be the variable. It must be the case that v is not 
> modified in the body of the for() loop. It must also be the case that 
> v is not modified after the for() loop, because v is declared in the 
> for()  loop INIT section. It must also be the case that the lambda is 
> contained in the body of the for() loop. Therefore, it is not possible 
> for v to be modified at any point in the source code of the program 
> that lexically follows the lambda. Therefore v is final or effectively 
> frozen at the point of capture" with respect to that lambda.

I get that! What I'm saying is that most users will read my above 
example like:

|for (int j = 0 ; j < 10 ; ) { ... j = j + i; } |

That is a good explanation for what the loop does. But this now breaks 
the generalization (because "j" is now mutated inside the body). E.g. 
the variable "j" is declared in the "for loop" statement. It is also 
modified in the for loop statement (in the STEP part). It seems mostly 
an implementation "trick" that we can look at STEP before BODY, so that 
we can then consider the induction variable as "not mutated after it is 
introduced".

Maurizio


> -AC
>
> -- 
> Archie L. Cobbs
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://mail.openjdk.org/pipermail/amber-dev/attachments/20241021/14e995f2/attachment.htm>


More information about the amber-dev mailing list