在Visual Studio QuickWatch中用LINQ处理WCF对象遇错误求助
这个问题我之前也碰到过,其实是你用的VS2019 16.7.3版本调试器的一个已知限制,具体原因和解决办法如下:
为什么会出现这个错误?
当你在QuickWatch里执行people.Select(x => x.DateOfBirth)这类返回IEnumerable<T>的LINQ查询时,调试器为了展示查询结果,会尝试访问Enumerable的SystemCore_EnumerableDebugView类的Items属性。而这个属性的底层实现调用了Microsoft.Win32.SafeNativeMethods.QueryPerformanceCounter这个原生方法——VS调试器在实时评估表达式的场景下,是不支持调用原生方法的,所以就抛出了你看到的错误。
而people.First().DateOfBirth能正常工作,是因为它只返回单个对象,调试器直接访问该对象的DateOfBirth属性,完全不会触发EnumerableDebugView的逻辑,自然也就不会调用那个不被支持的原生方法。
可行的解决办法
1. 改用非LINQ的数组转换方法
在QuickWatch里用Array.ConvertAll代替LINQ的Select,这个方法直接操作数组,不会返回IEnumerable<T>,也就不会触发DebugView的问题:
Array.ConvertAll(people, x => x.DateOfBirth)
2. 在代码中提前赋值集合
与其在QuickWatch里实时评估LINQ查询,不如在代码断点前加一行代码把结果存下来,之后直接查看这个变量:
var people = GetPeopleFromWCF().ToArray(); // 新增这行代码 var birthdays = people.Select(x => x.DateOfBirth).ToList(); // 在这里设置断点
断点暂停后直接查看birthdays变量,就能正常看到所有出生日期的列表了。
3. 升级Visual Studio版本
这个调试器的限制在VS2019的后续更新版本(比如16.11.x及以上)以及VS2022中已经被修复了。如果你可以升级的话,更新到较新的VS版本,就能直接在QuickWatch里正常使用LINQ查询了。
4. 在QuickWatch中手动枚举结果
如果不想改代码也不想升级,可以在QuickWatch里手动写一段枚举代码来提取属性,绕过DebugView的逻辑:
var birthdays = new List<DateTime>(); foreach(var person in people) { birthdays.Add(person.DateOfBirth); } birthdays
内容的提问来源于stack exchange,提问作者Daniil Palii

