我对背景工作者有疑问/问题。
我在win表单项目中使用VB.NET和EF5。主窗体有三个选项卡,每个选项卡都有一组不同的数据。我正在使用存储库和工作单元模式来访问我的所有数据。为了使UI线程不锁定,我决定使用后台工作程序在加载UI后填充每个列表。
最初在我的代码中,我在表单加载方法中有以下代码:
'//Set up tasks to obtain all the data from the DB and put it in the correct listviewitem format
AddHandler bgGetAllOpenOrders.DoWork, AddressOf BGAllOpenOrdersListGenerator
AddHandler bgGetAllNeedsAttention.DoWork, AddressOf BGAllNeedsAttentionOrdersListGenerator
AddHandler bgGetAllStock.DoWork, AddressOf BGStockListGenerator
'//Set up tasks to populate the relevant lists with the relevant data when all the data has been loaded.
AddHandler bgGetAllOpenOrders.RunWorkerCompleted, AddressOf BGPopulateAllOpenOrders
AddHandler bgGetAllNeedsAttention.RunWorkerCompleted, AddressOf BGPopulateNeedsAttentionList
AddHandler bgGetAllStock.RunWorkerCompleted, AddressOf BGPopulateStockList
'//Begin running of the loading code in the background whilst the form remains open to use.
bgGetAllOpenOrders.RunWorkerAsync()
bgAllNeedsAttention.RunWorkerAsync()
bgGetAllStock.RunWorkerAsync()
然而,这会导致各种问题,例如并不总是返回所有正确的数据,有时我会得到关于连接已经打开的错误(我尝试激活MARS,这没有帮助)
然后我将on load方法更改为以下内容:
'//Set up tasks to obtain all the data from the DB and put it in the correct listviewitem format
AddHandler bgGetAllOpenOrders.DoWork, AddressOf BGAllOpenOrdersListGenerator
AddHandler bgGetAllNeedsAttention.DoWork, AddressOf BGAllNeedsAttentionOrdersListGenerator
AddHandler bgGetAllStock.DoWork, AddressOf BGStockListGenerator
'//Set up tasks to populate the relevant lists with the relevant data when all the data has been loaded.
AddHandler bgGetAllOpenOrders.RunWorkerCompleted, AddressOf BGPopulateAllOpenOrders
AddHandler bgGetAllNeedsAttention.RunWorkerCompleted, AddressOf BGPopulateNeedsAttentionList
AddHandler bgGetAllStock.RunWorkerCompleted, AddressOf BGPopulateStockList
'//Begin running of the loading code in the background whilst the form remains open to use.
bgGetAllOpenOrders.RunWorkerAsync()
在BGPopulateAllOpenOrders
内部,我致电bgAllNeedsAttention.RunWorkerAsync()
,在BGPopulateNeedsAttentionList
内,我致电bgGetAllStock.RunWorkerAsync()
。这个(我认为)有一点同步性,但它有效,而且这个和旧方法之间的时差可以忽略不计,而且它总是返回正确的数据并且不会产生任何错误。
我想知道的是,这是一种反模式/不推荐,是否会导致我没有看到的任何问题?
答案 0 :(得分:1)
它会起作用,它不会“引起任何问题”。
另一方面,它不是一个非常好的模式,即难以维护。
考虑1 Bgw只按顺序运行3个方法。我稍微依赖于什么数据回来,以及何时/如何使用它。但是您可以轻松地使用Control.Invoke(Dispatcher.Invoke)返回主线程,Completed事件就是为您执行此操作。