Why is “reference” to an int (and not value) stored?
本问题已经有最佳答案,请猛点这里访问。
下面的代码段将输出数字"10"十次:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | delegate void Printer(); static void Main() { List<Printer> printers = new List<Printer>(); for (int i = 0; i < 10; i++) { printers.Add(delegate { Console.WriteLine(i); }); } foreach (var printer in printers) { printer(); } } |
这是因为(摘自https://www.toptal.com/c-sharp/interview questions iquestion-90455):
"the delegate is added in the for loop and"reference" to i is stored,
rather than the value itself. Therefore, after we exit the loop, the
variable i has been set to 10, so by the time each delegate is
invoked, the value passed to all of them is 10."
我的问题是:为什么要存储对我的"引用"?
This is because"the delegate is added in the for loop and"reference" to i is stored
不,这不是问题。问题在于如何提取委托和引用的值。这就是所谓的终结。从循环中提取委托,并且只保留EDOCX1的最后一个值(0),因为在循环之后运行闭包。(如果将其称为"中间",它将返回该时间的值)。
看看这篇博客文章,你会发现这个代表是如何在一个看似错误的地方被编译的。
这是它用来演示问题的代码:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | Func func1 = null; Program.<>c__DisplayClass2 class1 = new Program.<>c__DisplayClass2(); // <-- problem class1.i = 0; while (class1.i < count) { if (func1 == null) // <-- more problems to follow { func1 = new Func(class1.<fillFunc>b__0); // <-- yikes: just one func! } Program.funcArr[class1.i] = func1; class1.i++; // <-- and just one i } |
这不是按值与参照的效果。
输出值为10,因为当委托代码运行时(在第二个循环中)会评估变量EDOCX1的值(0),到那时将假定值为10,因为这是第一个循环退出时的结果。
使用调试器在第二个循环中单步执行对