簡體   English   中英

Haskell中並發性的奇怪行為

[英]Strange behavior with concurrency in Haskell

我有以下代碼:

import Control.Concurrent

sleepSort = mapM_ (forkIO . put)
  where put x = threadDelay (x*10000) >> print x

這對一組整數執行睡眠排序,並且工作正常,除了一個警告:

程序按順序打印出數據集中的每個數字,就像它應該的那樣。 但是,在完成打印出最后一個數字后,它會等待用戶鍵入一些數字,然后回顯該數字,然后完成。

我不認為我在任何時候都要求用戶輸入,為什么會發生這種情況呢?

發生這種情況是因為您的主線程不等待其他線程完成。 你的程序啟動n個線程,但主線程立即退出,然后你返回到解釋器提示符。 同時其他線程繼續產生輸出:

Prelude Control.Concurrent> sleepSort [1,2,3]
1
Prelude Control.Concurrent> 2
3

您可以通過向主線程添加延遲來解決此問題:

Prelude Control.Concurrent> sleepSort [1,2,3] >> threadDelay 10000
1
2
3

如果您正在運行已編譯的程序,它將立即退出而不打印任何內容:

$ cat Test.hs
import Control.Concurrent

sleepSort = mapM_ (forkIO . put)
  where put x = threadDelay (x*1000) >> print x

main = sleepSort [1,2,3]
$ ghc --make -O2 Test.hs
[1 of 1] Compiling Main             ( Test.hs, Test.o )
Linking Test ...
$ ./Test
$

更新:您可以在sleepSort函數中使用信號量,而不是threadDelay的調用添加到main

import Control.Concurrent
import Control.Concurrent.QSemN

sleepSort l = do
  qsem <- newQSemN 0
  mapM_ (forkIO . put qsem) l
  waitQSemN qsem n
  where
    n = length l
    put qsem x = threadDelay (x*1000) >> print x >> signalQSemN qsem 1

main = sleepSort [1,2,3]

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM