Closures and loop scope

Timon Gehr timon.gehr at gmx.ch
Tue Jun 4 16:10:27 PDT 2013


On 06/05/2013 12:42 AM, Andrei Alexandrescu wrote:
> On 6/4/13 5:03 PM, Nick Sabalausky wrote:
>> On Tue, 04 Jun 2013 21:19:56 +0200
>> "Idan Arye"<GenericNPC at gmail.com>  wrote:
>>
>>> Consider the following code. What will it print?
>>>
>>>       auto arr=new ulong delegate()[5];
>>>
>>>       foreach(i;0..arr.length){
>>>           arr[i]=()=>i;
>>>       }
>>>
>>>       writeln(arr.map!`a()`());
>>>
>>> It is natural to expect that it will print [0, 1, 2, 3, 4], but
>>> it actually prints [5, 5, 5, 5, 5]. The reason is obvious - all
>>> the delegates refer to the same `i` in their closures, and at the
>>> end of the loop that `i` is set to `5`.
>>>
>>
>> I think the problem is simply a misunderstanding of closures.
>
> FWIW this

By 'this' I assume you mean aliasing semantics of a foreach variable?

> was discussed at a C# conference. It was a change of behavior
> or something. It was a sort of a big deal, and a matter in which
> reasonable people were disagreeing.
>...

Due to its foreach lowering, the above is expected behaviour in C#.
D has a different lowering of foreach, and hence the above is an 
instance of http://d.puremagic.com/issues/show_bug.cgi?id=2043.


More information about the Digitalmars-d mailing list