2

現在の値から動作 (セル/ヴァル) を更新します。

ただし、次のコードは、MVar 操作の例外で無期限にブロックされたスレッドをスローします。

「iの値:」が3回出力されると予想していました。私は何を逃したのですか?- ありがとう。

  {-# LANGUAGE RecursiveDo #-}
  module Main where

  import           FRP.Sodium

  main :: IO ()
  main = do
    (e, t) <- sync newEvent

    rec
      b <- sync $ hold 0 $ snapshot (\_ i -> i + 1) e b

    sync $ listen (value b) (\i -> putStrLn $ "value of i: " ++ show i)

    sync $ t "ping"
    sync $ t "ping"
    sync $ t "ping"

    return ()

  • GHCi、バージョン 7.8.3
  • ナトリウム-0.11.0.3
4

1 に答える 1

2

再帰的な let fromRecursiveDoIOモナドにあります。モナドにReactiveMonadFixインスタンスがあります。b内で完全に定義してから、これを囲むようにReactive使用しsyncて、定義全体をトランザクションとして実行できます。

main = do
    (e, t) <- sync newEvent

    b <- sync $
        do
            rec
                b <- hold 0 $ snapshot (\_ i -> i + 1) e b
            return b

    sync $ listen (value b) (\i -> putStrLn $ "value of i: " ++ show i)

    ...

このRecursiveDo表記法は、この単純な例では役に立ちません。同じことは、 の観点からより簡単に記述できますmfix

main = do
    (e, t) <- sync newEvent

    b <- sync . mfix $ hold 0 . snapshot (\_ i -> i + 1) e

    sync $ listen (value b) (\i -> putStrLn $ "value of i: " ++ show i)

    ...

Behaviorからを作成することEventは通常 で行われることに言及する価値があるでしょうaccum

b <- sync $ accum 0 (const (+1) <$> e)

holdナトリウムでは、これは派生関数であり、 、snapshot、およびで内部的に定義されていmfixます。

accum :: Context r => a -> Event r (a -> a) -> Reactive r (Behavior r a)
accum z efa = do
    rec
        s <- hold z $ snapshot ($) efa s
    return s
于 2015-05-02T19:56:58.767 に答える