[Haskell-cafe] Precise timing

Jeffrey Brown jeffbrown.the at gmail.com
Sun Oct 19 01:36:04 UTC 2014


Hi,

An earlier version of this question is cross-posted at StackOverflow
<http://stackoverflow.com/questions/26437770/timing-inaccuracy-in-haskell-threaddelay>
.

What should I use for precise (and eventually, concurrency-compatible)
timing in Haskell? I want to make rhythms. I tried the following to produce
a repeating rhythm in which one note is twice as long as the other two.
(That rhythm is encoded by the list [1,1,2].)

    import Control.Concurrent
    import Text.Printf
    import Control.Monad

    main = mapM_ note (cycle [1,1,2])

    beat = round (10^6 / 4) -- measured in microseconds

    note :: Int -> IO ()
    note n = do
        threadDelay $ beat * n
        printf "\BEL\n"

When I run it the long note is three times as long as the others, not
twice. If I speed it up, by changing the number 4 to a 10, the rhythm is
destroyed completely: the notes all have the same length.

threadDelay is guaranteed
<http://hackage.haskell.org/package/base-4.7.0.1/docs/Control-Concurrent.html#v:threadDelay>
to
wait at least as long, but potentially longer than, what the caller
specifies. Another potential problem could be buffering in printf.
(Eventually I intend to replace the printf statement with OSC output to a
sound generator.)

Thanks,
Jeff
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://www.haskell.org/pipermail/haskell-cafe/attachments/20141018/721548e1/attachment.html>


More information about the Haskell-Cafe mailing list