3 ms·
> Maybe “loop body” would make the comment clearer? I think "loop iteration" might.
by nemetroid 4y ago
> Maybe “loop body” would make the comment clearer?
I think "loop iteration" might.
- foldr 4y agoArguably not, because an 'iteration' is a unit of execution, not a lexical unit. If the variables were really scoped to loop iterations, that would be a form of dynamic scope, which would have a different semantics. So for example, say the loop calls a function foo. This function executes inside every iteration of the loop, but within foo, one cannot access the loop iteration variable (as it is in a different lexical context).
- nemetroid 4y agoMy point is precisely that lexical terms (like loop body) are insufficient to explain the Go behaviour. The loop variable is clearly lexically scoped to the loop body. "Scoping loop variables outside the loop" is commonly understood as the Python gotcha: for x in range(3): foo(x) print(x) # prints 2 or the pre-C99 style: int i; for (i = 0; i < 3; ++i) foo(i) printf("%d", i); // prints 3 This is not the case in Go. I don't think talking about variable scopes accurately describes the issue (because there's nothing special about loop scopes here: the same "escape" can happen from any scope), and changing "loop" to "loop body" doesn't improve this. The term "loop iteration" at least identifies the dependency between different iterations of the loop as the issue. I don't understand what the thought experiment about non-lexical scopes has to do with this.
- foldr 4y agoIt's purely a question of scopes, as indicated by the equivalent code in the article: for _, elem := range elems { elem := elem ... &elem ... } Nothing beyond regular lexical scoping and Go's ordinary assignment semantics are necessary to see how this works. The second 'elem' has a narrower scope than the first (it is limited to the loop body). Abusing Go syntax, you can think of the current semantics as follows: { var elem Elem for _, elem = range elems { ... &elem ... } } Here 'elem' scopes outside the loop body, and so is reassigned on every iteration of the loop (and &elem evaluates to the same address on every iteration). >the thought experiment about non-lexical scopes It's not just a thought experiment. There are languages with dynamically scoped variables (e.g. global vars in Common Lisp).