我目前正试图让我的函数在backgroundworker.CancellationPending == true
时自行取消。
我有一个这样的课程:
public class ImportPostManager
{
public event ProgressChangedEventHandler ProgressChanged;
protected virtual void OnProgressChanged(int progress)
{
if (ProgressChanged != null)
{
ProgressChanged(this, new ProgressChangedEventArgs(progress, null));
}
}
public void DoSomeStuff()
{
while(something == true)
{
if(backgroundworker.CancellationPending) return; //Here's my problem
//KeepDoingStuff and report progress
}
}
}
我从backgroundworker.DoWork()
中的表单调用该函数但是如何让该类听取backgroundworker.CancellationPending
?我无法在.DoWork()
中执行此操作,因为它看起来像这样:
void _progressDialog_DoWork(object sender, DoWorkEventArgs e)
{
Managers.ImportPostManager.Instance.ProgressChanged += (s, pe) => dialog.ReportProgress(pe.ProgressPercentage, null, pe.ProgressPercentage.ToString() + "%);
Managers.ImportPostManager.Instance.DoSomeStuff();
}
...而且我不想将背景工作者发送到函数.DoSomeStuff()
。有没有办法使用事件或东西来获得我想要的东西?我还没有找到任何可以解释如何以我能理解的方式......
答案 0 :(得分:0)
如果你在DoSomeStuff
出售而没有直接通过工作人员,并假设它是阻止的(看起来是公平的),你最好的选择可能是添加一个Func<bool>
函数的参数。
public void DoSomeStuff(Func<bool> ShouldCancel)
{
while (whatever == whateverElse && !ShouldCancel())
{
// Do work
}
}
然后你可以从你的DoWork
处理程序中调用它。
void _progressDialog_DoWork(object sender, DoWorkEventArgs e)
{
Managers.ImportPostManager.Instance.ProgressChanged += (s, pe) => dialog.ReportProgress(pe.ProgressPercentage, null, pe.ProgressPercentage.ToString() + "%);
Managers.ImportPostManager.Instance.DoSomeStuff(() => backgroundworker.CancellationPending);
}
每次都会得到评估,生活会很好。
虽然如果您担心这样的情况发生了很多,但是可能值得研究一种更高级的多线程形式,即使只是通过System.Threading.Tasks
命名空间提供的形式。在那里,您将有更多选择取消。但是如果你正在寻找快速而简单的东西,那么添加该函数就可以解决问题了,并且它可以在多个上下文中工作,所以如果你选择反对它,那么你的助手类将不会与后台工作者的使用联系在一起。将来
当然,如果您没有使用BackgroundWorker.CancellationPending
属性(或者,如果我没记错,Cancel()
方法),您可以更改该功能并检查{{ 1}},只需针对该CancellationToken
调用(或者更确切地说,针对其Cancel()
)。这在某些方面并不理想,但是如果你想要转向更多的东西,就像我之前说过的那样,那将会更加清洁。当然,如果你现在已经设置了这个功能,你也可以很容易地在CancellationTokenSource
之上层叠令牌,所以根据你的选择,你不能永远地选择一个或另一个时刻。