Thursday, December 3, 2015

Variable Capture and Loops

Tim Ekl:

The difference, it turns out, has to do with how variables are bound in loops, and how values are captured in anonymous functions. The Swift (and Objective-C) behavior – which I was most used to at the time of writing – was to bind i as a different immutable value in each loop iteration, then capture a reference to that value each time through.

Go, on the other hand, binds a single mutable value for the entire loop, then captures a reference to that single variable instead, only getting the value in question at the time the function is executed.

[…]

Interestingly enough, we can even “introduce” this bug in Swift code by using a C-like loop instead of the nicer forin syntax[…] Since this style explicitly uses a single mutable i for the entire loop, rather than binding a new i for each iteration, the “buggy” behavior – printing five sixes – occurs. Swift is even kind enough to make the mutability of i here more explicit, by requiring it be annotated var in the loop declaration.

See also: Capturing references in closures, Capture Lists, The __block Storage Type.

Comments RSS · Twitter

Leave a Comment