【问题标题】:Implicitly defined variable throws run-time error while explicitly defined does not隐式定义的变量会引发运行时错误,而显式定义则不会
【发布时间】:2017-12-05 15:21:35
【问题描述】:

使用 VB.NET,我正在尝试按照 ReSharper 的指南清理代码库。我目前有以下代码:

'oSearchInput is defined outside this question
Dim oSearchRoutines As New SearchClient
Dim oSearchResults As List(Of SearchResult)

oSearchRoutines = 'WcfCallThatReturnsSearchClient

oSearchResults = oSearchRoutines.getSearchResults(oSearchInput).ToList

现在这完全可以正常工作,但 ReSharper 警告 As New SearchClient 有“分配的值未在任何执行路径中使用”。所以我删除了那部分以获得这段代码:

'oSearchInput is defined outside this question
Dim oSearchRoutines
Dim oSearchResults As List(Of SearchResult)

oSearchRoutines = 'WcfCallThatReturnsSearchClient

oSearchResults = oSearchRoutines.getSearchResults(oSearchInput).ToList

如果我理解正确,那么一切都应该完全一样。但是调用ToList时会报错:

未找到类型“SearchResult()”上的公共成员“ToList”。

我不确定为什么我这里的两个 sn-ps 之间有任何区别。

【问题讨论】:

  • As New SearchClient 不仅仅是声明类型,它还创建了对象。如果稍后您从 Wcf 方法分配对象,则第一个未使用并且无缘无故地创建。第二个声明 Dim oSearchRoutines 不会在 Option Strict 下编译,它只是 System.Object。您可以声明一个类型而不创建它:Dim oSearchRoutines As SearchClient
  • 我不完全确定,但我认为错误消息是由后期绑定和扩展方法的交集引起的。 ToList是Linq提供的扩展方法,所以当你显式声明oSearchRoutines的类型时,编译器知道如何找到ToList,但是当它是Object类型时,运行时解析找不到扩展方法。

标签: .net vb.net winforms resharper


【解决方案1】:

因为您在第二个示例中没有分配 SearchClient 类型,所以 oSearchRoutines 将自动成为 Object 类型。

Object 类型的表达式主要不允许使用Extension methods,例如ToList 方法。欲了解更多信息,请参阅here

以下示例说明了这种行为:

Dim x As Object
Dim y As String = "ABC"
x = y

Dim a As List(Of Char) = y.ToList() 'This will work
Dim b As List(Of Char) = x.ToList() 'This will throw a System.MissingMemberException

出现消息Value assigned is not used in any execution path,因为您在第一个示例中使用New 声明oSearchRoutines。 这是不必要的,因为您正在为其分配一个新值...

oSearchRoutines = 'WcfCallThatReturnsSearchClient

...在任何地方使用它之前。

因此你可以在没有关键字New的情况下声明它

Dim oSearchRoutines As SearchClient

相关问题:VB.NET: impossible to use Extension method on System.Object instance

【讨论】:

  • 我认为您的诊断并不完全正确。 VB 可以并且确实对Object 变量进行后期绑定,实际上这似乎正在这里发生。错误不是没有getSearchResults方法,而是getSearchResults的返回类型没有ToList
  • @Craig 感谢您的评论。我已经编辑了我的答案。问题不在于编译器找不到扩展方法,而是出于安全原因不允许使用它。
猜你喜欢
  • 1970-01-01
  • 2015-03-08
  • 1970-01-01
  • 1970-01-01
  • 2017-02-02
  • 2010-10-15
  • 2011-10-27
  • 2015-04-21
  • 1970-01-01
相关资源
最近更新 更多