强类型泛型方法调用其参数的基类方法,而不是 T 中的隐藏方法?
考虑一个包含 Show()
隐藏实现的 MyForm
类。它还包含一个 CreateForm()
方法,该方法接受表单的实例并调用影子子:
Public Class MyForm
Inherits Form
Public Shadows Sub Show()
MessageBox.Show("Shadowed implementation called!")
End Sub
End Class
...
Public Sub CreateForm(ByVal childForm As MyForm)
childForm.MdiParent = Me
childForm.Show()
childForm.Focus()
End Sub
当使用 CreateForm(New MyForm())
调用时,影子实现Show()
被正确调用。现在考虑以下泛型实现:
Public Sub CreateForm(Of T As Form)(ByVal childForm As T)
childForm.MdiParent = Me
childForm.Show()
childForm.Focus()
End Sub
使用 CreateForm(Of MyForm)(New MyForm())
调用,此强类型泛型方法从不调用隐藏方法。
这是一个错误,还是我错过了什么?
Consider a MyForm
class that contains a shadowed implementation of Show()
. It also contains a CreateForm()
method, which accepts an instance of the form and calls the shadowed sub:
Public Class MyForm
Inherits Form
Public Shadows Sub Show()
MessageBox.Show("Shadowed implementation called!")
End Sub
End Class
...
Public Sub CreateForm(ByVal childForm As MyForm)
childForm.MdiParent = Me
childForm.Show()
childForm.Focus()
End Sub
When called with CreateForm(New MyForm())
, the shadowed implementation of Show()
is correctly called. Now consider the following generic implementation:
Public Sub CreateForm(Of T As Form)(ByVal childForm As T)
childForm.MdiParent = Me
childForm.Show()
childForm.Focus()
End Sub
Called with CreateForm(Of MyForm)(New MyForm())
, this strongly-typed generic method never invokes the shadowed method.
Is this a bug, or am I missing something?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
此行为是“设计使然”。这里要记住的技巧是泛型方法是由其自身编译和验证的(而不是像 C++ 那样在调用者的上下文中)。因此,泛型方法只知道
T
与Form
相关。它不了解MyForm
,因此可以正确绑定到Form
上的方法。这是正确的,因为
Shadows
方法仅在编译时与引用的类型一起发挥作用,使Shadow
方法可见。这里的情况并非如此,因为编译类型的引用类型是Form
(不是MyForm)
。这与Overridable
形成鲜明对比,后者的行为根据运行时类型而变化。This behavior is "By Design". The trick to remember here is that the generic method is compiled and verified by itself (not in the context of the caller as is done in C++). Hence the generic method only knows that
T
is related toForm
. It has no knowledge ofMyForm
and hence correctly binds to methods onForm
.This is correct because
Shadows
methods only come into play with the type of the reference at compile time makes theShadow
method visible. This is not the case here as the reference type at compile type isForm
(notMyForm)
. This is in contrast toOverridable
where the behavior changes based on the runtime type.你错过了一些东西。它只知道它在编译时处理表单(请记住,泛型不是模板!)。您唯一可以做的就是使用(覆盖)虚拟方法而不是隐藏它们。
另请参阅VB.NET 中的“阴影”与“覆盖”了解更多信息关于阴影的信息 - 这实际上不是多态性。
You're missing something. It only knows that it is dealing with a Form at compile-time (remember that generics are not templates!). The only thing you can do is use (override) virtual methods instead of shadowing them.
See also 'Shadows' vs. 'Overrides' in VB.NET for more info on shadowing - that's not actually polymorphism.
这不是一个错误,因为编译器仅根据应用于
T
的给定类型约束(即Form
)静态评估调用。编译器无法预测实际类型可能包含隐藏方法声明或已知父级(即Form
)中未声明的任何其他方法。It's not a bug because the call is evaluated by the compiler statically based just on the given type constraints applied to
T
, that isForm
. The compiler cannot predict the actual type could contain a shadowed method declaration or whatever other method not declared in the known parent (i.e.Form
).