Thread.Join 方法

定义

在此实例表示的线程终止前,阻止调用线程。

重载

Join()

在继续执行标准的 COM 和 SendMessage 消息泵处理期间,阻止调用线程,直到由该实例表示的线程终止。

Join(Int32)

在继续执行标准的 COM 和 SendMessage 消息泵处理期间,阻止调用线程,直到由该实例表示的线程终止或经过了指定时间为止。

Join(TimeSpan)

在继续执行标准的 COM 和 SendMessage 消息泵处理期间,阻止调用线程,直到由该实例表示的线程终止或经过了指定时间为止。

Join()

Source:
Thread.cs
Source:
Thread.cs
Source:
Thread.cs

在继续执行标准的 COM 和 SendMessage 消息泵处理期间,阻止调用线程,直到由该实例表示的线程终止。

public:
 void Join();
public void Join ();
member this.Join : unit -> unit
Public Sub Join ()

例外

调用方尝试加入处于 Unstarted 状态的线程。

线程在等待时中断。

注解

Join 是一种同步方法,它阻止调用线程 (即调用方法的线程) ,直到调用其方法的 Join 线程完成。 使用此方法可确保线程已终止。 如果线程未终止,调用方将无限期阻止。 在以下示例中 Thread1 ,线程调用 Join()Thread2方法,这会导致 Thread1 在完成之前 Thread2 阻止。

using System;
using System.Threading;

public class Example
{
   static Thread thread1, thread2;
   
   public static void Main()
   {
      thread1 = new Thread(ThreadProc);
      thread1.Name = "Thread1";
      thread1.Start();
      
      thread2 = new Thread(ThreadProc);
      thread2.Name = "Thread2";
      thread2.Start();   
   }

   private static void ThreadProc()
   {
      Console.WriteLine("\nCurrent thread: {0}", Thread.CurrentThread.Name);
      if (Thread.CurrentThread.Name == "Thread1" && 
          thread2.ThreadState != ThreadState.Unstarted)
         thread2.Join();
      
      Thread.Sleep(4000);
      Console.WriteLine("\nCurrent thread: {0}", Thread.CurrentThread.Name);
      Console.WriteLine("Thread1: {0}", thread1.ThreadState);
      Console.WriteLine("Thread2: {0}\n", thread2.ThreadState);
   }
}
// The example displays output like the following:
//       Current thread: Thread1
//       
//       Current thread: Thread2
//       
//       Current thread: Thread2
//       Thread1: WaitSleepJoin
//       Thread2: Running
//       
//       
//       Current thread: Thread1
//       Thread1: Running
//       Thread2: Stopped
open System.Threading

let mutable thread1, thread2 =
    Unchecked.defaultof<Thread>, Unchecked.defaultof<Thread>

let threadProc () =
    printfn $"\nCurrent thread: {Thread.CurrentThread.Name}"

    if
        Thread.CurrentThread.Name = "Thread1"
        && thread2.ThreadState <> ThreadState.Unstarted
    then
        thread2.Join()

    Thread.Sleep 4000
    printfn $"\nCurrent thread: {Thread.CurrentThread.Name}"
    printfn $"Thread1: {thread1.ThreadState}"
    printfn $"Thread2: {thread2.ThreadState}\n"

thread1 <- Thread threadProc
thread1.Name <- "Thread1"
thread1.Start()

thread2 <- Thread threadProc
thread2.Name <- "Thread2"
thread2.Start()

// The example displays output like the following:
//       Current thread: Thread1
//
//       Current thread: Thread2
//
//       Current thread: Thread2
//       Thread1: WaitSleepJoin
//       Thread2: Running
//
//
//       Current thread: Thread1
//       Thread1: Running
//       Thread2: Stopped
Imports System.Threading

Module Example
   Dim thread1, thread2 As Thread

   Public Sub Main()
      thread1 = new Thread(AddressOf ThreadProc)
      thread1.Name = "Thread1"
      thread1.Start()
      
      thread2 = New Thread(AddressOf ThreadProc)
      thread2.Name = "Thread2"
      thread2.Start()   
   End Sub

   Private Sub ThreadProc()
      Console.WriteLine()
      Console.WriteLine("Current thread: {0}", Thread.CurrentThread.Name)
      If (Thread.CurrentThread.Name = "Thread1" And 
          thread2.ThreadState <> ThreadState.Unstarted)
         thread2.Join()
      End If
      Thread.Sleep(4000)
      Console.WriteLine()
      Console.WriteLine("Current thread: {0}", Thread.CurrentThread.Name)
      Console.WriteLine("Thread1: {0}", thread1.ThreadState)
      Console.WriteLine("Thread2: {0}", thread2.ThreadState)
      Console.WriteLine()
   End Sub
End Module
' The example displays output like the following :
'       Current thread: Thread1
'       
'       Current thread: Thread2
'       
'       Current thread: Thread2
'       Thread1: WaitSleepJoin
'       Thread2: Running
'       
'       
'       Current thread: Thread1
'       Thread1: Running
'       Thread2: Stopped

如果在调用 时 Join 线程已终止,该方法将立即返回。

警告

永远不要从当前 Join 线程调用 表示当前线程的 对象的 方法 Thread 。 这会导致应用无响应,因为当前线程无限期地等待自身,

此方法将调用线程的状态更改为包含 ThreadState.WaitSleepJoin。 不能在处于 状态ThreadState.Unstarted的线程上调用 Join

另请参阅

适用于

Join(Int32)

Source:
Thread.cs
Source:
Thread.cs
Source:
Thread.cs

在继续执行标准的 COM 和 SendMessage 消息泵处理期间,阻止调用线程,直到由该实例表示的线程终止或经过了指定时间为止。

public:
 bool Join(int millisecondsTimeout);
public bool Join (int millisecondsTimeout);
member this.Join : int -> bool
Public Function Join (millisecondsTimeout As Integer) As Boolean

参数

millisecondsTimeout
Int32

等待线程终止的毫秒数。

返回

如果线程已终止,则为 true;如果 false 参数指定的时间量已过之后还未终止线程,则为 millisecondsTimeout

例外

millisecondsTimeout 的值为负数,且不等于 Infinite(以毫秒为单位)。

该线程尚未启动。

millisecondsTimeout 小于 -1 (Timeout.Infinite)。

线程在等待时中断。

注解

Join(Int32) 是阻止调用线程的同步方法 (即调用方法的线程) ,直到调用其方法的 Join 线程已完成或超时间隔已过。 在下面的示例中 Thread1 ,线程调用 Join()Thread2方法,这会导致 Thread1 阻塞直到 Thread2 完成或 2 秒已过。

using System;
using System.Threading;

public class Example
{
   static Thread thread1, thread2;
   
   public static void Main()
   {
      thread1 = new Thread(ThreadProc);
      thread1.Name = "Thread1";
      thread1.Start();
      
      thread2 = new Thread(ThreadProc);
      thread2.Name = "Thread2";
      thread2.Start();   
   }

   private static void ThreadProc()
   {
      Console.WriteLine("\nCurrent thread: {0}", Thread.CurrentThread.Name);
      if (Thread.CurrentThread.Name == "Thread1" && 
          thread2.ThreadState != ThreadState.Unstarted)
         if (thread2.Join(2000))
            Console.WriteLine("Thread2 has termminated.");
         else
            Console.WriteLine("The timeout has elapsed and Thread1 will resume.");   
      
      Thread.Sleep(4000);
      Console.WriteLine("\nCurrent thread: {0}", Thread.CurrentThread.Name);
      Console.WriteLine("Thread1: {0}", thread1.ThreadState);
      Console.WriteLine("Thread2: {0}\n", thread2.ThreadState);
   }
}
// The example displays the following output:
//       Current thread: Thread1
//       
//       Current thread: Thread2
//       The timeout has elapsed and Thread1 will resume.
//       
//       Current thread: Thread2
//       Thread1: WaitSleepJoin
//       Thread2: Running
//       
//       
//       Current thread: Thread1
//       Thread1: Running
//       Thread2: Stopped
open System.Threading

let mutable thread1, thread2 =
    Unchecked.defaultof<Thread>, Unchecked.defaultof<Thread>

let threadProc () =
    printfn $"\nCurrent thread: {Thread.CurrentThread.Name}"

    if
        Thread.CurrentThread.Name = "Thread1"
        && thread2.ThreadState <> ThreadState.Unstarted
    then
        if thread2.Join 2000 then
            printfn "Thread2 has termminated."
        else
            printfn "The timeout has elapsed and Thread1 will resume."

    Thread.Sleep 4000
    printfn $"\nCurrent thread: {Thread.CurrentThread.Name}"
    printfn $"Thread1: {thread1.ThreadState}"
    printfn $"Thread2: {thread2.ThreadState}\n"

thread1 <- Thread threadProc
thread1.Name <- "Thread1"
thread1.Start()

thread2 <- Thread threadProc
thread2.Name <- "Thread2"
thread2.Start()

// The example displays the following output:
//       Current thread: Thread1
//
//       Current thread: Thread2
//       The timeout has elapsed and Thread1 will resume.
//
//       Current thread: Thread2
//       Thread1: WaitSleepJoin
//       Thread2: Running
//
//
//       Current thread: Thread1
//       Thread1: Running
//       Thread2: Stopped
Imports System.Threading

Module Example
   Dim thread1, thread2 As Thread

   Public Sub Main()
      thread1 = new Thread(AddressOf ThreadProc)
      thread1.Name = "Thread1"
      thread1.Start()
      
      thread2 = New Thread(AddressOf ThreadProc)
      thread2.Name = "Thread2"
      thread2.Start()   
   End Sub

   Private Sub ThreadProc()
      Console.WriteLine()
      Console.WriteLine("Current thread: {0}", Thread.CurrentThread.Name)
      If (Thread.CurrentThread.Name = "Thread1" And 
          thread2.ThreadState <> ThreadState.Unstarted)
         If thread2.Join(TimeSpan.FromSeconds(2))
            Console.WriteLine("Thread2 has termminated.")
         Else
            Console.WriteLine("The timeout has elapsed and Thread1 will resume.")
         End If      
      End If
      Thread.Sleep(4000)
      Console.WriteLine()
      Console.WriteLine("Current thread: {0}", Thread.CurrentThread.Name)
      Console.WriteLine("Thread1: {0}", thread1.ThreadState)
      Console.WriteLine("Thread2: {0}", thread2.ThreadState)
      Console.WriteLine()
   End Sub
End Module
' The example displays the following output:
'       Current thread: Thread1
'       
'       Current thread: Thread2
'       
'       Current thread: Thread2
'       Thread1: WaitSleepJoin
'       Thread2: Running
'       
'       
'       Current thread: Thread1
'       Thread1: Running
'       Thread2: Stopped

如果 Timeout.InfinitemillisecondsTimeout 参数指定了 ,则此方法的行为与 Join() 方法重载相同,但返回值除外。

如果在调用 时 Join 线程已终止,该方法将立即返回。

此方法将调用线程的状态更改为包含 ThreadState.WaitSleepJoin。 不能在处于 状态ThreadState.Unstarted的线程上调用 Join

另请参阅

适用于

Join(TimeSpan)

Source:
Thread.cs
Source:
Thread.cs
Source:
Thread.cs

在继续执行标准的 COM 和 SendMessage 消息泵处理期间,阻止调用线程,直到由该实例表示的线程终止或经过了指定时间为止。

public:
 bool Join(TimeSpan timeout);
public bool Join (TimeSpan timeout);
member this.Join : TimeSpan -> bool
Public Function Join (timeout As TimeSpan) As Boolean

参数

timeout
TimeSpan

设置等待线程终止的时间量的 TimeSpan

返回

如果线程已终止,则为 true;如果 false 参数指定的时间量已过之后还未终止线程,则为 timeout

例外

的 值为 timeout 负,不等于 Infinite 以毫秒为单位,或大于 Int32.MaxValue 毫秒。

调用方尝试加入处于 Unstarted 状态的线程。

示例

下面的代码示例演示如何将 值与 方法一 TimeSpan 起使用 Join

using namespace System;
using namespace System::Threading;

static TimeSpan waitTime = TimeSpan(0,0,1);

ref class Test
{
public:
   static void Work()
   {
      Thread::Sleep( waitTime );
   }

};

int main()
{
   Thread^ newThread = gcnew Thread( gcnew ThreadStart( Test::Work ) );
   newThread->Start();
   if ( newThread->Join( waitTime + waitTime ) )
   {
      Console::WriteLine( "New thread terminated." );
   }
   else
   {
      Console::WriteLine( "Join timed out." );
   }
}
// The example displays the following output:
//        New thread terminated.
using System;
using System.Threading;

class Test
{
    static TimeSpan waitTime = new TimeSpan(0, 0, 1);

    public static void Main() 
    {
        Thread newThread = new Thread(Work);
        newThread.Start();

        if(newThread.Join(waitTime + waitTime)) {
            Console.WriteLine("New thread terminated.");
        }
        else {
            Console.WriteLine("Join timed out.");
        }
    }

    static void Work()
    {
        Thread.Sleep(waitTime);
    }
}
// The example displays the following output:
//        New thread terminated.
open System
open System.Threading

let waitTime = TimeSpan(0, 0, 1)

let work () =
    Thread.Sleep waitTime

let newThread = Thread work
newThread.Start()

if waitTime + waitTime |> newThread.Join then
    printfn "New thread terminated."
else
    printfn "Join timed out."

// The example displays the following output:
//        New thread terminated.
Imports System.Threading

Public Module Test
    Dim waitTime As New TimeSpan(0, 0, 1)

    Public Sub Main() 
        Dim newThread As New Thread(AddressOf Work)
        newThread.Start()

        If newThread.Join(waitTime + waitTime) Then
            Console.WriteLine("New thread terminated.")
        Else
            Console.WriteLine("Join timed out.")
        End If
    End Sub

    Private Sub Work()
        Thread.Sleep(waitTime)
    End Sub
End Module
' The example displays the following output:
'       New thread terminated.

注解

Join(TimeSpan) 是阻止调用线程的同步方法 (即调用方法的线程) ,直到调用其方法的 Join 线程已完成或超时间隔已过。 在下面的示例中 Thread1 ,线程调用 Join()Thread2方法,这会导致 Thread1 阻塞直到 Thread2 完成或 2 秒已过。

using System;
using System.Threading;

public class Example
{
   static Thread thread1, thread2;
   
   public static void Main()
   {
      thread1 = new Thread(ThreadProc);
      thread1.Name = "Thread1";
      thread1.Start();
      
      thread2 = new Thread(ThreadProc);
      thread2.Name = "Thread2";
      thread2.Start();   
   }

   private static void ThreadProc()
   {
      Console.WriteLine("\nCurrent thread: {0}", Thread.CurrentThread.Name);
      if (Thread.CurrentThread.Name == "Thread1" && 
          thread2.ThreadState != ThreadState.Unstarted)
         if (thread2.Join(TimeSpan.FromSeconds(2)))
            Console.WriteLine("Thread2 has termminated.");
         else
            Console.WriteLine("The timeout has elapsed and Thread1 will resume.");   
      
      Thread.Sleep(4000);
      Console.WriteLine("\nCurrent thread: {0}", Thread.CurrentThread.Name);
      Console.WriteLine("Thread1: {0}", thread1.ThreadState);
      Console.WriteLine("Thread2: {0}\n", thread2.ThreadState);
   }
}
// The example displays the following output:
//       Current thread: Thread1
//       
//       Current thread: Thread2
//       The timeout has elapsed and Thread1 will resume.
//       
//       Current thread: Thread2
//       Thread1: WaitSleepJoin
//       Thread2: Running
//       
//       
//       Current thread: Thread1
//       Thread1: Running
//       Thread2: Stopped
open System
open System.Threading

let mutable thread1, thread2 =
    Unchecked.defaultof<Thread>, Unchecked.defaultof<Thread>

let threadProc () =
    printfn $"\nCurrent thread: {Thread.CurrentThread.Name}"

    if
        Thread.CurrentThread.Name = "Thread1"
        && thread2.ThreadState <> ThreadState.Unstarted
    then
        if TimeSpan.FromSeconds 2 |> thread2.Join then
            printfn "Thread2 has termminated."
        else
            printfn "The timeout has elapsed and Thread1 will resume."

    Thread.Sleep 4000
    printfn $"\nCurrent thread: {Thread.CurrentThread.Name}"
    printfn $"Thread1: {thread1.ThreadState}"
    printfn $"Thread2: {thread2.ThreadState}\n"

thread1 <- Thread threadProc
thread1.Name <- "Thread1"
thread1.Start()

thread2 <- Thread threadProc
thread2.Name <- "Thread2"
thread2.Start()

// The example displays the following output:
//       Current thread: Thread1
//
//       Current thread: Thread2
//       The timeout has elapsed and Thread1 will resume.
//
//       Current thread: Thread2
//       Thread1: WaitSleepJoin
//       Thread2: Running
//
//
//       Current thread: Thread1
//       Thread1: Running
//       Thread2: Stopped
Imports System.Threading

Module Example
   Dim thread1, thread2 As Thread

   Public Sub Main()
      thread1 = new Thread(AddressOf ThreadProc)
      thread1.Name = "Thread1"
      thread1.Start()
      
      thread2 = New Thread(AddressOf ThreadProc)
      thread2.Name = "Thread2"
      thread2.Start()   
   End Sub

   Private Sub ThreadProc()
      Console.WriteLine()
      Console.WriteLine("Current thread: {0}", Thread.CurrentThread.Name)
      If (Thread.CurrentThread.Name = "Thread1" And 
          thread2.ThreadState <> ThreadState.Unstarted)
         If thread2.Join(2000)
            Console.WriteLine("Thread2 has termminated.")
         Else
            Console.WriteLine("The timeout has elapsed and Thread1 will resume.")
         End If      
      End If
      Thread.Sleep(4000)
      Console.WriteLine()
      Console.WriteLine("Current thread: {0}", Thread.CurrentThread.Name)
      Console.WriteLine("Thread1: {0}", thread1.ThreadState)
      Console.WriteLine("Thread2: {0}", thread2.ThreadState)
      Console.WriteLine()
   End Sub
End Module
' The example displays the following output:
'       Current thread: Thread1
'       
'       Current thread: Thread2
'       
'       Current thread: Thread2
'       Thread1: WaitSleepJoin
'       Thread2: Running
'       
'       
'       Current thread: Thread1
'       Thread1: Running
'       Thread2: Stopped

如果 Timeout.Infinitetimeout指定了 ,则此方法的行为与 Join() 方法重载相同,但返回值除外。

如果在调用 时 Join 线程已终止,该方法将立即返回。

此方法将当前线程的状态更改为包含 WaitSleepJoin。 不能在处于 状态ThreadState.Unstarted的线程上调用 Join

另请参阅

适用于