欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

VB.NET并行与分布式编程(6)-线程与内核同步[6]

程序员文章站 2022-04-29 11:30:10
...

1、

1)WaitHandle.WaitAny 方法和WaitHandle.WaitAll方法的区别在于,WaitAny方法只等待指定数组中的任一元素收到信号。

2)我们使用WaitHandle.WaitAny 方法完成一个示例,这个示例同时使用5个线程完成相同的工作:计算从1到2000的累加,哪个线程最先完成计算任务,就终止其它正在计算的线程。为了增强效果,我们指定最后一个线程的优先级最高,结果应是最后一个线程最先完成计算,其它线程被终止

2、代码如下:

Imports System
Imports System.Threading
Imports System.Diagnostics
Imports System.Diagnostics.ThreadState











Module Module1

    <MTAThread()> _
    Sub Main()





        '完成任务的线程号
        Dim finishedid As Integer
        '自己创建线程对象数组(不使用.NET的线程池),共5个线程
        Dim mythread(4) As Thread
        '分别给每个线程创建一个AutoResetEvent
        Dim threadevent(4) As AutoResetEvent
        For i = 0 To mythread.GetUpperBound(0)
            mythread(i) = New Thread(AddressOf mythreadrun)
            threadevent(i) = New AutoResetEvent(False)
            mythread(i).Name = "thread_" & i
        Next
        Console.WriteLine(Now.ToLongTimeString & "线程对象创建完毕,开始执行线程")
        mythread(4).Priority = ThreadPriority.AboveNormal
        '执行线程
        For i = 0 To mythread.GetUpperBound(0)
            mythread(i).Start(threadevent(i))
        Next
        '等待其中一个线程完成累加,然后将其它未完成任务的线程终止 
        finishedid = WaitHandle.WaitAny(threadevent)
        For i = 0 To mythread.GetUpperBound(0)
            If i <> finishedid Then
                mythread(i).Abort()
            End If
        Next
        '线程执行完毕
        Console.WriteLine(Now.ToLongTimeString & "    " & finishedid & "号线程完成任务,计算完毕!")
    End Sub
    Public Sub mythreadrun(ByVal threadevent As Object)
        Dim mynum As Integer
        Dim jg As ULong = 0
        Try
            For mynum = 1 To 2000
                jg += mynum
                Thread.Sleep(5)
            Next
            Console.WriteLine(Thread.CurrentThread.Name & "  " & Now.ToLongTimeString & "线程运行完毕!")
            Console.WriteLine(Thread.CurrentThread.Name & "==>" & Now.ToLongTimeString & "=>计算结果为:" & jg)
        Catch
            Console.WriteLine(Thread.CurrentThread.Name & "  " & Now.ToLongTimeString & "线程异常终止!")
            '终止线程
            Thread.CurrentThread.Abort()
        Finally
            CType(threadevent, AutoResetEvent).Set()
        End Try
    End Sub
End Module

 3、效果如下:


VB.NET并行与分布式编程(6)-线程与内核同步[6]
            
    
    博客分类: .net&silverlight  
 

 

4、代码分析如下:

1)  创建一个简单的线程池以及每个线程使用的AutoResetEvent

         '完成任务的线程号
        Dim finishedid As Integer
        '自己创建线程对象数组(不使用.NET的线程池),共5个线程
        Dim mythread(4) As Thread
        '分别给每个线程创建一个AutoResetEvent
        Dim threadevent(4) As AutoResetEvent

 

注意finishedid将保存最先完成任务的线程号

2)对线程池的每个线程对象初始化,指定名称。同时也初始化AutoResetEvent数组

        For i = 0 To mythread.GetUpperBound(0)
            mythread(i) = New Thread(AddressOf mythreadrun)
            threadevent(i) = New AutoResetEvent(False)
            mythread(i).Name = "thread_" & i
        Next

3)指定4号线程的优先级,比其它线程池的线程要高,同时启动线程,将AutoResetEvent数组中的元素做为参数传进线程中

        mythread(4).Priority = ThreadPriority.AboveNormal
        '执行线程
        For i = 0 To mythread.GetUpperBound(0)
            mythread(i).Start(threadevent(i))
        Next

4) 等待其中一个线程完成累加:

        finishedid = WaitHandle.WaitAny(threadevent)

      将其它未完成任务的线程终止 :
        For i = 0 To mythread.GetUpperBound(0)
            If i <> finishedid Then
                mythread(i).Abort()
            End If
        Next

5)线程函数中完成累加,并输出结果

           For mynum = 1 To 2000
                jg += mynum
                Thread.Sleep(5)
            Next
            Console.WriteLine(Thread.CurrentThread.Name & "  " & Now.ToLongTimeString & "线程运行完毕!")
            Console.WriteLine(Thread.CurrentThread.Name & "==>" & Now.ToLongTimeString & "=>计算结果为:" & jg)
 6)设置 AutoResetEvent对象状态

        Finally
            CType(threadevent, AutoResetEvent).Set()

 

  • VB.NET并行与分布式编程(6)-线程与内核同步[6]
            
    
    博客分类: .net&silverlight  
  • 大小: 43.1 KB