Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Haskell - Some questions about System.Process and multithreading

I have a small numerical simulation in C (I had to do it in C to share it with my advisor) but I want to use a "haskell script" like thing to organize the simulation. The program accepts some command line arguments and spits some output I'd like to redirect to a file, so I did something like this:

 import Control.Monad
 import System.Process

I have a function to create the name of the output file:

filename :: Int -> String  
filename n = some stuff here...

and the command I wanna run:

command :: Int -> String
command n = "./mycutesimulation " ++ show n ++ " >" ++ filename n

and finally I produce a list of the runs I wanna make and run them in with runCommand:

commands = map command [1,2..1000]

main = do
   sequence_ $ map runCommand commands

The problem is that after I run this "script", my computer almost freezes with the load. The program that is being executed is very light in memory use and runs in a fraction of a second. This shouldn't happen.

So, my questions are:

1) Did I just threw 1000 processes to be executed at the same time??? How can I execute them in a rational order - sequentially or just a few processes at a time.

2)I'm running this in a quad core and it'd be nice to use this in my favour. Is there a way I can compile this with that -threaded flag and get the processes to be concurrently executed but in an organized way?

like image 526
Rafael S. Calsaverini Avatar asked Feb 28 '23 18:02

Rafael S. Calsaverini


1 Answers

You need a waitForProcess =<< runCommand.

import System.Process

main = sequence $ map (\x -> runCommand x) commands
 where commands = map (\x -> "echo " ++ show x) [1, 2..1000]

has similar symptoms to yours, but

import System.Process

main = sequence $ map (\x -> waitForProcess =<< runCommand x) commands
 where commands = map (\x -> "echo " ++ show x) [1, 2..1000]

works.

like image 121
Aidan Cully Avatar answered Mar 05 '23 11:03

Aidan Cully