
foreach l f = mapM_ f l
... rename to forM_ as per previous emails ... I would like to add to this. The previous loop runs the code once independantly for each item in the list. Sometimes you want to carry state through the loop: v = init foreach x list do code v = update v (I know that this can be done with IORefs, but ignoring that for now) for looping with a carried variable: forXM_ init [] f = () forXM_ init (x:xs) f = do i' <- f init x forXM_ i' xs f or with a returned value (the carried variable at the end of the loop): forXM init [] f = init forXM init (x:xs) f = do i' <- f init x forXM i' xs f used as: forXM_ 0 [1,2,3,4] (\x n -> putStrLn $ unwords [show x, " -> ", show n] return $ x + n ) looping a fixed number of times when the loop index is not needed: loopM_ n f = forM_ [1..n] (\n -> f) used as: loopM_ 5 ( print "hello" ) with a carried variable (with and without a result): loopXM_ i n f = forXM_ i [1..n] (\x n -> f x) loopXM i n f = forXM i [1..n] (\x n -> f x) (is this related to foldM_?) used as: loopXM_ 1 5 (\x -> print x return (x * x + x) ) do..while loop with a carried variable: untilXM_ i p f = do i' <- f i when (p i') (untilXM_ f i') untilXM i p f = do i' <- f i if (p i') then (untilXM_ f i') else (return i') used as: untilXM_ 1 (< 100) (\x -> print x return (x * x + x) ) Some of these also make sense in pure-functional code (obviously not the ones with no return values). For example the following iteration with a loop-carried variable: s = 0 foreach n [1,2,3,4] s += n return s is "foldl (+) 0 [1,2,3,4]" and we can mimic the syntax by reordering the arguments: forX i l f = foldl f i l forX 0 [1,2,3,4] (\x n -> x + n ) Obviously many of these examples can be rewritten easily without using these constructs, but as was pointed out earlier in the thread, larger, more complicated programs are more difficult to juggle around. These constructs are fairly easy to understand, at least for people coming from an imperative background... I recently rewrote a small (a few hundred lines of code) imperative program in haskell using these constructs without changing the structure of the code very much. Maybe I'm missing the point somewhat (I'm still learning haskell) by trying to mimick imperative constructs in haskell, but the translation was much simpler (and mechanical) this way... Tim Newsham http://www.thenewsh.com/~newsham/