Sam*_*Sam 2 .net f# asynchronous
我是F#Async工作流程的新手.通常,介绍此主题的代码和示例包含以下示例(简化):
let sleepWorkflow =
async{
printfn "Starting sleep workflow at %O" DateTime.Now.TimeOfDay
do! Async.Sleep 2000
printfn "Finished sleep workflow at %O" DateTime.Now.TimeOfDay
}
Async.RunSynchronously sleepWorkflow
Run Code Online (Sandbox Code Playgroud)
我试图理解与其do! Async.Sleep 2000相反的需要do Threading.Thread.Sleep(2000).
根据我的理解,BOTH方法将在此时同步运行代码.
有什么区别(我认为必须有),什么时候应该使用一种方法而不是另一种?
区别在于使用Thread.Sleep阻塞当前线程以便在Async.Sleep创建系统计时器时不能执行任何其他操作,释放当前线程(以便它可以执行其他操作)然后(在时间过去之后)再次获取线程并运行其余的代码.
如果你有大量async并行运行的工作流(因为每个工作流程都很昂贵)或者你在GUI线程上运行代码(只有一个线程,你不应该阻止它),这很重要.
为了更好地理解这一点,您可以将线程池线程数更改为1,并使用同步和异步阻塞尝试以下代码:
System.Threading.ThreadPool.SetMinThreads(1, 1)
System.Threading.ThreadPool.SetMaxThreads(1, 1)
for i in 1 .. 5 do
async { System.Threading.Thread.Sleep(1000)
printfn "Done" } |> Async.Start
for i in 1 .. 5 do
async { do! Async.Sleep(1000)
printfn "Done" } |> Async.Start
Run Code Online (Sandbox Code Playgroud)
运行第一个for循环后,您将打印"完成"消息,延迟时间为1秒(因为一个线程被重复阻止1秒).
运行第二个for循环后,您将看到1秒钟后立即打印"完成"消息.这是因为异步等待实际上并没有阻塞线程,因此5个定时器将全部经过,然后使用1个可用线程进行打印(这几乎不需要时间).
| 归档时间: |
|
| 查看次数: |
80 次 |
| 最近记录: |