I believe I have discovered a bona fide compiler bug that's demonstrated with this simple script:
As I understand it, j in the for loop is not local to the loop. Do I have this wrong?
The first int j is declared in the context of void setup() and outside of the loop and is not given a value.
A second instance of int j is then declared inside the context of the loop and given a value of 10. It exists only within that context and its value of 10 is printed while the loop is running.
The last print occurs outside the loop and therefore reports the value of the first instance of int j that was declared earlier within the setup() function context. Since this particular instance of the variable has not yet been assigned a value, the value returned is 0.
That is not the case. A different variable named j is declared as part of the for loop initialisation. It is this variable that is given a value of 10 and is printed in the for loop whilst the other variable with the same name is printed after the for loop
No. That j is an uninitialised local variable and just happens to be zero. The value "returned" when it is used is whatever was in the memory location the compiler uses for it, it could literally be anything.
Using it in that manner also makes for undefined behaviour, which means literally anything can happen.
Sorry, my explanation here was indeed insufficient. Yes, as it was called on an unassigned variable, the serial.print statement could have returned any unpredictable value within the scope of an int as described. It just so happened that the value was zero in this case.