我在面试任务中找到了这段代码。结果取决于调试。为什么Value
在调试模式下发生了变化?请解释一下它是如何工作的。
static IEnumerable<int> Square(IEnumerable<int> a)
{
foreach (var r in a)
{
Console.WriteLine(r * r);
yield return r * r;
}
}
class Wrap
{
private static int init = 0;
public int Value1
{
get { return ++init; }
}
}
static void Main(string[] args)
{
var w = new Wrap();
var wraps = new Wrap[3];
for (int i = 0; i < wraps.Length; i++)
{
wraps[i] = w;
}
var values = wraps.Select(x => x.Value1);
var results = Square(values);
int sum = 0;
int count = 0;
foreach (var r in results)
{
count++;
sum += r;
}
Console.WriteLine("Count {0}", count);
Console.WriteLine("Sum {0}", sum);
Console.WriteLine("Count {0}", results.Count());
Console.WriteLine("Sum {0}", results.Sum());
}
例如: 没有任何断点的正常输出
1
4
9
伯爵3 总和14
16个
25个
36个
伯爵3 49个
64个
81个
总和194
但是,如果您应该将断点放在wraps[i] = w;
附近并多次展开值
你可以得到类似的东西:
16
25个
36个
伯爵3 总和77
49个
64个
81个
伯爵3 100个
121个
144个
总和365
甚至更大。结果取决于您在调试模式下观察变量值的次数。为什么?
我正在调试器中运行,逐步执行代码并检查属性
答案 0 :(得分:5)
如果设置断点并使用观察窗口观察Value1
,调试器将访问此属性。
通过访问Value1
,执行getter代码,因此
get { return ++init; }
init
增加1
。