我有一段代码使用DataTable
从DbDataAdapter
填充数据库表。
DbDataAdapter
是通过DbProviderFactory.CreateDataAdapter
方法创建的,其中DbProviderFactory
由Devart dotConnect提供。
我们使用Devart的驱动程序用于Oracle,SqlServer和Postgres。
由于我的DataTable
中有近100k行,我需要绑定到RowUpdated
事件(更新进度条),遗憾的是,它没有在公共接口上定义,尽管它可用在所有提到的数据库驱动程序中。
因此我通过反射用这段代码绑定它:
Dim eventInfo As System.Reflection.EventInfo = adapter.GetType().GetEvent("RowUpdated")
eventInfo.AddEventHandler(adapter, [Delegate].CreateDelegate(eventInfo.EventHandlerType,
(Sub(s As Object, e As EventArgs) UpdateProgress(s, e)).Method))
如果使用VS2013编译,这完全有效,但如果在Roslyn(VS2015)上编译,则 在运行时 会失败,但有以下异常:
无法绑定到目标方法,因为其签名或安全透明度与委托类型的方法不兼容
对此有何帮助?
使用Devart.Data.PostgreSql.PgSqlRowUpdatedEventHandler
(我目前在Postgres上)作为e
的类型无效。
答案 0 :(得分:0)
从@djv评论中发布的this answer开始,我终于找到了罪魁祸首。
看来,使用Roslyn(VS2015),您需要在绑定事件处理程序之前显式声明Delegate
。
例如,在我的情况下,我需要写:
Public Delegate Sub RowUpdatedEventHandler(sender As Object, e As RowUpdatedEventArgs)
然后:
Dim eventInfo As System.Reflection.EventInfo = adpt.GetType().GetEvent("RowUpdated")
eventInfo.AddEventHandler(adpt, [Delegate].CreateDelegate(eventInfo.EventHandlerType,
DirectCast(AddressOf UpdateProgress, RowUpdatedEventHandler).Method))
它似乎与lamdas有一些问题。例如,这不起作用:
Dim eventInfo As System.Reflection.EventInfo = adpt.GetType().GetEvent("RowUpdated")
eventInfo.AddEventHandler(adpt, [Delegate].CreateDelegate(eventInfo.EventHandlerType,
DirectCast((Sub(s As Object, e As RowUpdatedEventArgs) UpdateProgress(s, e)), RowUpdatedEventHandler).Method))
(在lambda表达式上有或没有DirectCast
)