http://blogs.msdn.com/b/ericlippert/archive/2009/11/12/closi...
It could always be worse, though. Look at JavaScript. Simply copying the loop variable in the body of the loop doesn't work because all variables are scoped at the function level. So your "local" loop variable is actually a single instance for the entire function and you have the same exact problem. Instead, you have to actually create another function and immediately execute it with the loop iteration variable as an argument, and then use the parameter within the function to do whatever you wanted to do. Not cool.
It really was a horrible wart that needed to be fixed.
Now if they would only fix the misleading lying dishonest "downcast on type bound" compiler error messages, then C# would lack warts all together.
Consider (stolen from the spec doc):
In previous versions of C#, there is a single value variable is in the scope of the entire loop, so the above code would actually print out the last value in the list because that was the value of value (sorry) when the loop finished. In C# 5.0, a value variable is actually in the scope of each individual iteration (so within the braces). So now if you use your iteration variable in a closure scope it won't change on you when the loop iterates and the above code actually prints out the first value.The same cannot be said for a for loop. It still functions as it always has.