【问题标题】:Why the FirstOrDefault search on IEnumerable<Row> based on RowIndex doesn't work in debug windows?为什么基于 RowIndex 的 IEnumerable<Row> 上的 FirstOrDefault 搜索在调试窗口中不起作用?
【发布时间】:2017-06-03 08:21:45
【问题描述】:

下面的代码行基于 RowIndex 对 IEnumerable 执行 FirstOrDefault 搜索,但在调试窗口(在 Watch、Quick watch 和 Immediate 窗口)中不起作用。它会在这些窗口中引发 System.NullReferenceException。我正在使用 Visual Studio 2015 更新 3。

sheetdata.Descendants<Row>().FirstOrDefault(p => p.RowIndex.Value == 2U)

但是当我将它转换为列表并执行相同的搜索时,它可以在这些调试窗口中工作。为什么会出现这种差异?

sheetdata.Descendants<Row>().ToList().FirstOrDefault(p => p.RowIndex.Value == 2U)

当我运行代码时,不存在这种差异。只有当我尝试在这些调试窗口中调试代码时才能看到这种差异。

【问题讨论】:

  • “不起作用”根本无法描述您所看到的内容。请澄清,并提供minimal reproducible example。
  • Convert.ToUInt32(2)) 天哪。 2u
  • 这并不能解决问题。我通过避免转换来更新问题。

标签: c# ienumerable openxml watch immediate-window


【解决方案1】:

我认为 OpenXml 的 QueryProvider 在处理 Convert.ToUInt32(2) 时存在问题,因为他需要将其翻译成它自己的语言(如 SQL 的 QueryProvider)。

您应该尽量避免在谓词中进行转换并提前进行,因为并非所有 QueryProviders 都支持所有功能并可能引发异常(主要是 NotSupportedException)。

uint value = Convert.ToUInt32(2);
sheetdata.Descendants<Row>().FirstOrDefault(p => p.RowIndex.Value == value)

调用.ToList() 将在内存中执行此操作,因为它会从您的工作表中读取所有值,然后找到第一个匹配值。

【讨论】:

  • 您可以将uint 类型的值二写成2u 并直接使用它。 C# 编译器和任何 Linq 提供者都将更好地了解 2u 是什么,与他们可能没有意识到其含义的方法调用 Convert.ToUInt32(2) 相比。此外,在== 的操作数的上下文中,您可以只使用2,因为C# 编译器将足够聪明地选择正确的类型。但2u 对人类读者来说更准确。
  • 感谢您的回复。但这并不能解决问题。我通过避免转换来更新问题。
猜你喜欢
  • 1970-01-01
  • 2018-09-30
  • 1970-01-01
  • 2023-01-25
  • 2016-10-16
  • 2020-11-25
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多