代码之家  ›  专栏  ›  技术社区  ›  Edward Tanguay

如何中止一个线程并使代码仍在该线程中执行?

  •  0
  • Edward Tanguay  · 技术社区  · 16 年前

    一本书作为下面的例子,解释说你不会看到“嫁妆已经结束”这一行:

    …因为线程被中止 当做嫁妆的时候 线程睡眠

    这是有道理的,但什么是 古怪的 如果你把第一个睡眠时间改为6000,让嫁接线有时间完成5000个睡眠,那么嫁接线 打印“Dowork has ended”,但这是在Dowork线程 流产的 , 那么,如果在那一点上嫁妆线已经中止,那么打印“嫁妆结束”的线是什么? (它似乎在那一点上运行 流产的 线程)

    using System;
    using System.Threading;
    
    namespace TestThreading838
    {
        class Program
        {
            static void Main(string[] args)
            {
                Console.WriteLine("MAIN THREAD started.");
    
                Thread DoWorkThread = new Thread(new ThreadStart(DoWork));
    
                DoWorkThread.Start();
                Thread.Sleep(1000); //if you change this to 6000 you see "DoWork has ended."
    
                DoWorkThread.Abort();
    
                Console.WriteLine("MAIN THREAD ending...");
                Thread.Sleep(6000);
                Console.WriteLine("MAIN THREAD ended.");
    
                Console.ReadLine();
            }
    
            public static void DoWork()
            {
                Console.WriteLine("DoWork is running.");
                try
                {
                    Thread.Sleep(5000);
                }
                catch (ThreadAbortException ex)
                {
                    Console.WriteLine("DoWork was aborted.");
                }
                finally
                {
                    Console.WriteLine("DoWork cleaning up after being aborted.");
                }
                Console.WriteLine("DoWork has ended."); //never shown
            }
    
        }
    }
    
    3 回复  |  直到 16 年前
        1
  •  3
  •   Jon Skeet    16 年前

    如果您将第一个睡眠时间更改为6000,那么第二个线程将在您中止它之前完成它需要做的所有事情-它不是真正中止的,因为您刚刚调用了 Abort 在一条已经死了的线上。注意,不会打印“DoWork was aborted”…

    尝试打印 DoWorkThread.ThreadState 在你打电话之前 中止 -我很肯定你会看到它“停了”。

        2
  •  1
  •   Guillaume    16 年前

    “DoWork has ended”正在第二个线程(DoWorkThread)上运行。

        DoWorkThread.Start(); //Run the thread
        Thread.Sleep(6000); //Let the thread run for 6sec so "DoWork has ended" will be displayed
        DoWorkThread.Abort();
    
        3
  •  0
  •   Donald Byrd    16 年前

    除非调用thread.resetabort(),否则threadabortexception将自动重新引发。因此,在捕获后,系统会重新执行它,并最终执行,但此时它将成为未处理的异常,因此“DoWork has ended.”永远不会打印。