Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    text
    copied!<p>Implementing your desired <code>timed</code> on top of <code>System.Timeout.timeout</code> is easy:</p> <pre><code>import System.Timeout (timeout) timed :: Int -&gt; IO a -&gt; b -&gt; IO (Either b a) timed us act def = liftM (maybe (Left def) Right) (timeout us act) </code></pre> <p>By the way, the common implementation of <code>timeout</code> is closer to this: (<code>$!</code> = <code>seq</code> to try to force evaluation of the returned value in the thread rather than only returning a thunk):</p> <pre><code>import Control.Concurrent (forkIO, threadDelay, killThread) import Control.Concurrent.MVar (newEmptyMVar, putMVar, takeMVar) import System.IO (hPrint, stderr) timeout :: Int -&gt; IO a -&gt; IO (Maybe a) timeout us act = do mvar &lt;- newEmptyMVar tid1 &lt;- forkIO $ (putMVar mvar . Just $!) =&lt;&lt; act tid2 &lt;- forkIO $ threadDelay us &gt;&gt; putMVar mvar Nothing res &lt;- takeMVar mvar killThread (maybe tid1 (const tid2) res) `catch` hPrint stderr return res </code></pre> <p>The implementation of <code>System.Timeout.timeout</code> in the libraries is a little more complex, handling more exceptional cases.</p> <pre><code>import Control.Concurrent (forkIO, threadDelay, myThreadId, killThread) import Control.Exception (Exception, handleJust, throwTo, bracket) import Data.Typeable import Data.Unique (Unique, newUnique) data Timeout = Timeout Unique deriving Eq timeoutTc :: TyCon timeoutTc = mkTyCon "Timeout" instance Typeable Timeout where { typeOf _ = mkTyConApp timeoutTc [] } instance Show Timeout where show _ = "&lt;&lt;timeout&gt;&gt;" instance Exception Timeout timeout n f | n &lt; 0 = fmap Just f | n == 0 = return Nothing | otherwise = do pid &lt;- myThreadId ex &lt;- fmap Timeout newUnique handleJust (\e -&gt; if e == ex then Just () else Nothing) (\_ -&gt; return Nothing) (bracket (forkIO (threadDelay n &gt;&gt; throwTo pid ex)) (killThread) (\_ -&gt; fmap Just f)) </code></pre>
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload