0

我是 winforms 编程的新手,我开始使用线程。

我已经设法启动了一个线程,但现在我希望能够单击取消按钮来停止该线程。

到目前为止,这是我的代码...

这将启动线程:

private void btnSessions_Click(object sender, EventArgs e)
{
    Thread downloadThread = new Thread(new ThreadStart(DownloadThread));
    downloadThread.Start();
}

这是线程:

void DownloadThread()
{
     // Do the work
}

这是我想用来取消线程的按钮:

private void btnCancel_Click(object sender, EventArgs e)
{
     // Stop the thread
}

谁能帮我弄清楚我需要在 btnCancel_Click 中添加什么?

4

3 回答 3

3

您应该为此使用任务并行库 (TPL),它支持取消任务的自然方式:

private CancellationTokenSource _tokenSource2;
private CancellationToken _token;

private void btnSessions_Click(object sender, EventArgs e)
{
    _tokenSource2 = new CancellationTokenSource();
    _token = _tokenSource2.Token;

    Task task = Task.Run(() => DownloadThread(), _token);
}

private void DownloadThread()
{
    while (true)
    {
        //do work

        //cancel if needed
        if (_token.IsCancellationRequested)
        {
            _token.ThrowIfCancellationRequested();
        }
    }
}

private void btnCancel_Click(object sender, EventArgs e)
{
    // Stop the thread
    _tokenSource2.Cancel();
}

有关取消任务的更多信息:http: //msdn.microsoft.com/en-us/library/dd997396 (v=vs.110).aspx

为什么不应该使用Thread.Abort使用Thread.Abort() 有什么问题

于 2013-11-12T13:21:23.007 回答
2

您需要将 downloadThread 设为对象中的一个字段:

Thread downloadThread; 
private void btnSessions_Click(object sender, EventArgs e)
{
     downloadThread = new Thread(new ThreadStart(DownloadThread));
     downloadThread.Start();
}

void DownloadThread()
{
     // Do the work
}

private void btnCancel_Click(object sender, EventArgs e)
{
     downloadThread.Abort();
}

后台工作人员将是 ui 相关处理的更好解决方案。

于 2013-11-12T13:15:56.383 回答
0

最好不要使用Thread,尤其是Thread.Abort对于这样的任务。C# 具有隐藏线程的高级抽象包装器。只需使用TaskCancellationToken。这是示例:

var cts = new CancellationTokenSource(); // define in class
CancellationToken ct = cts.Token;

private void btnSessions_Click(object sender, EventArgs e)
{
    Task.Factory.StartNew(() => DownloadThread(), ct ); // start task
}

private void DownloadThread()
{
    // You need to check this at some point where cancel may occur
    if (ct.IsCancellationRequested)
        ct.ThrowIfCancellationRequested();
}

private void btnCancel_Click(object sender, EventArgs e)
{
    cancelToken.Cancel(false); // cancel task
}

更多信息可以在msdn上找到

于 2013-11-12T13:20:38.603 回答