0

我有一个线程,我试图停止。我所做的是以下。

randomImages = new Thread(new ThreadStart(this.chooseRandomImage));
            randomImages.Start();

这是线程调用的方法

bool threadAlive = true;
public void chooseRandomImage()
    {
        while(threadAlive)
        {
           try
            {
                //do stuff


            }

            catch (Exception exe)
            {
                MessageBox.Show(exe.Message, "Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }


        }
    }

现在,单击停止线程按钮后,我只需将 threadAlive 设置为 false。问题是线程不会立即停止,就好像它已经聚集了一种动力。如何立即停止线程,并可能再次重新启动它?

 private void butStopThread_Click(object sender, EventArgs e)
    {

        threadAlive = false;


        if(threadAlive == false)
        {
           //do stuff
        }


    }
4

3 回答 3

2

对不起,这是最好的方法。向上使用 .NET 4.0,您应该使用任务,而不是线程,然后有一个叫做 CancellationToken 的东西与您的变量几乎相同。

然后,取消后,等待处理完成。如果这需要快速发生,那么 - 好吧 - 使取消检查更加细化,即更频繁地检查。

如http://www.interact-sw.co.uk/iangblog/2004/11/12/cancellation中所述,中止线程可能具有显着的副作用- 这就是通常不应使用该方法的原因。

不,停止的线程等不能神奇地重新启动 - 你必须将它放入你的逻辑中(重新启动点,保存点,长时间运行的事务,记住它在哪里完成)。

作为旁注 - 如果您坚持不使用任务并且可以访问 .NET 的最新版本,那么如果您使用互锁访问类方法,则不需要 Volatile,这之前是一些根据定义是线程安全的汇编程序指令。

于 2013-01-05T11:36:40.987 回答
1

可以通过调用 Abort 从另一个线程终止一个线程,但这会强制终止受影响的线程,而不用担心它是否已完成其任务并且没有提供清理资源的机会。此示例中显示的技术是首选。

您需要使用Abort 方法, 但不推荐使用

于 2013-01-05T11:21:20.937 回答
0

根据您提供的信息,工作线程和 UI 线程似乎都在访问threadAlive变量。尝试使用volatile关键字声明 threadAlive ,以确保在没有同步问题的情况下进行跨线程访问。

volatile bool threadAlive;

要重新启动线程,您首先需要确保它执行所有必要的清理。在主/UI 线程中对您的线程对象使用Join方法调用,以确保您的线程安全终止。要重新启动,只需在线程上调用 Start 方法。

randomImages.Join();
于 2013-01-05T11:41:43.817 回答