Skip to content

Instantly share code, notes, and snippets.

@phagenlocher
Last active March 19, 2023 03:21
Show Gist options
  • Save phagenlocher/353b24d969598198ca009e055eb2482d to your computer and use it in GitHub Desktop.
Save phagenlocher/353b24d969598198ca009e055eb2482d to your computer and use it in GitHub Desktop.
-- Compile with -threaded
import System.IO
import Control.Concurrent
import Control.Concurrent.STM
-- (<Sum>, <Number of finished transactions>)
type Result = TVar (Int, Int)
-- Adds x to result and increments the number of finished transactions
addToResult :: Result -> Int -> STM ()
addToResult result x = do
(sum, endCtr) <- readTVar result
writeTVar result (sum+x, endCtr+1)
-- Waits for the number of finished transactions to reach a limit
-- Then returns the sum of the result
waitForCounter :: Result -> Int -> STM Int
waitForCounter result limit = do
(sum, endCtr) <- readTVar result
if endCtr < limit then retry else return sum
main :: IO ()
main = do
-- Number of threads to spawn
let n = 100
-- Set up TVar
result <- atomically $ newTVar (0, 0)
-- Spawn threads
mapM_ (\x -> forkIO $ atomically $ addToResult result x) [1..n]
-- Wait for threads to finish and get sum
sum <- atomically $ waitForCounter result n
-- Print sum
putStrLn $ "Sum [1..n] = " ++ show sum
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment