首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >WaitOne()函数的正确用法是什么

WaitOne()函数的正确用法是什么
EN

Stack Overflow用户
提问于 2013-08-08 13:12:24
回答 1查看 1.5K关注 0票数 1

我实验了一些线程池的例子。我从MSDN网站上的Fibonacci示例开始,但是这不适合于64次以上的计算,所以我用下面的代码进行了解析:

代码语言:javascript
复制
Imports System.Threading

Module Module1
    Public Class Fibonacci
        Private _n As Integer
        Private _fibOfN
        Private _doneEvent As ManualResetEvent

        Public ReadOnly Property N() As Integer
            Get
                Return _n
            End Get
        End Property

        Public ReadOnly Property FibOfN() As Integer
            Get
                Return _fibOfN
            End Get
        End Property

        Sub New(ByVal n As Integer, ByVal doneEvent As ManualResetEvent)
            _n = n
            _doneEvent = doneEvent
        End Sub

        ' Wrapper method for use with the thread pool.
        Public Sub ThreadPoolCallBackMar(ByVal threadContext As Object)
            Dim threadIndex As Integer = CType(threadContext, Integer)
            Console.WriteLine("thread {0} started...", threadIndex)
            _fibOfN = Calculate(_n)
            Console.WriteLine("thread {0} result calculated...", threadIndex)
            _doneEvent.Set()
        End Sub

        Public Function Calculate(ByVal n As Integer) As Integer
            If n <= 1 Then
                Return n
            End If
            Return Calculate(n - 1) + Calculate(n - 2)
        End Function

    End Class


    <MTAThread()>
    Sub Main()
        Const FibonacciCalculations As Integer = 65

        ' One event is used for each Fibonacci object
        Dim doneEvents(FibonacciCalculations) As ManualResetEvent
        Dim fibArray(FibonacciCalculations) As Fibonacci
        Dim r As New Random()

        ' Configure and start threads using ThreadPool.
        Console.WriteLine("launching {0} tasks...", FibonacciCalculations)

        For i As Integer = 0 To FibonacciCalculations
            doneEvents(i) = New ManualResetEvent(False)
            Dim f = New Fibonacci(r.Next(20, 40), doneEvents(i))
            fibArray(i) = f
            ThreadPool.QueueUserWorkItem(AddressOf f.ThreadPoolCallBackMar, i)
        Next

        Console.WriteLine("All calculations are complete.")

        For i As Integer = 0 To FibonacciCalculations
            doneEvents(i).WaitOne()
            Dim f As Fibonacci = fibArray(i)
            Console.WriteLine("Fibonacci({0}) = {1}", f.N, f.FibOfN)
        Next

        Console.Read()
    End Sub
End Module

使用WaitOne()而不是WaitAll()解决了问题,但问题是:如果我不需要显示结果,那么我不需要第二个循环,但是.在没有第二个循环的情况下,我必须将waitOne()函数放在哪里?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2013-08-08 14:40:09

您的代码本质上是这样做的:

代码语言:javascript
复制
// start a bunch of threads to do calculations

Console.WriteLine("All calculations are complete."); // This is a lie!

// Wait for the threads to exit

这里的主要问题是,当您调用Console.WriteLine时,计算还没有完成。嗯,它们可能是完整的,但你不知道,除非你已经等待事件的信号。

WaitOne的目的是告诉您计算是否已经完成。您的代码应该如下所示:

代码语言:javascript
复制
    For i As Integer = 0 To FibonacciCalculations
        doneEvents(i) = New ManualResetEvent(False)
        Dim f = New Fibonacci(r.Next(20, 40), doneEvents(i))
        fibArray(i) = f
        ThreadPool.QueueUserWorkItem(AddressOf f.ThreadPoolCallBackMar, i)
    Next

    Console.WriteLine("All calculations are started. Waiting for them to complete.")

    For i As Integer = 0 To FibonacciCalculations
        doneEvents(i).WaitOne()
        Dim f As Fibonacci = fibArray(i)
        Console.WriteLine("Fibonacci({0}) = {1}", f.N, f.FibOfN)
    Next

    Console.WriteLine("All calculations are complete.")

必须检查事件,才能知道计算已完成。

现在,如果您不需要知道计算是否完成,那么根本不需要WaitOne。如果你不打算等待这个事件,那么就没有真正的需要举办这个活动了,是吗?虽然有人想知道为什么你要做一个计算,然后不使用结果。

票数 3
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/18126979

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档