取消winforms中的工作线程

Jos*_*osh 4 c# multithreading backgroundworker winforms

我有两个列表框,一个是主人,另一个是孩子.当索引在主服务器上更改时,子列表框将适当地填充与主服务器相关的记录.当一个主人需要很长时间才能获得所有记录并且在完成记录之前,用户点击一个花费更少时间填充的不同主人时,我的问题就出现了.最后,即使用户不在那个主人身上,那么花费更长时间的主人也会填充子列表框.

我一直在使用BackgroundWorker线程进行填充.

bw_LoadAll.DoWork += new DoWorkEventHandler(bg_LoadAllWork);
bw_LoadAll.RunWorkerCompleted += new RunWorkerCompletedEventHandler(bg_LoadAllWorkCompleted);
bw_LoadAll.WorkerSupportsCancellation = true;
Run Code Online (Sandbox Code Playgroud)

我订阅了master的SelectedIndexChanged事件,并将取消的等于true设置为:

bw_LoadAll.CancelAsync();
Run Code Online (Sandbox Code Playgroud)

以下是DoWork方法中的代码:

List<object> s = Repository.Instance().LoadAll();
if (!bw_LoadAll.CancellationPending) {
    e.Result = s;
} else {
    e.Cancel = true;
}
Run Code Online (Sandbox Code Playgroud)

但由于某种原因,完成的工作人员的代码不断被调用.这是工人完成的代码:

if (!e.Cancelled) {
    ddl.DataSource = e.Result;
    ddl.DisplayMember = "QuickName";
    ddl.ValueMember = "ID";
}
Run Code Online (Sandbox Code Playgroud)

还有什么我必须做的才能取消这个线程返回吗?

Ree*_*sey 5

您的方法bg_LoadAllWork应定义为:

void bg_LoadAllWork(object sender, DoWorkEventArgs e)
{
    // Do your work here...
} 
Run Code Online (Sandbox Code Playgroud)

在bg_LoadAllWork内部,您需要检查e.CancellationPending,如果是,则设置e.Cancel = true;

最后一部分很重要 - 如果你从未设置过e.Cancel,那么你的"e.Cancelled"将永远不会成立.对CancelAsync的调用实际上并没有取消任何东西 - 它更像是"请求后台工作取消自己" - 你必须放置逻辑以导致取消.