递归地更新“行为".钠产生的“线程阻塞..." [英] recursive update a "Behaviour" in Sodium yields 'thread blocked ...'

查看:78
本文介绍了递归地更新“行为".钠产生的“线程阻塞..."的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我将从当前值更新行为(单元格/值).

i would update a Behaviour (Cell / Val) from it's current value.

,但是以下代码引发在MVar操作中被无限期阻塞的线程.

我期望它会打印三倍的"i:值". 我想念什么? -谢谢.

i have expected it prints three times 'value of i: '. what did i missing? - thanks.

  {-# 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

    • GHCi, version 7.8.3
    • sodium-0.11.0.3
    • 推荐答案

      您从RecursiveDo进行的递归租赁位于IO monad中. Reactive monad也有一个MonadFix实例.您可以完全在Reactive中定义b,然后使用 sync 围绕它执行,以将整个定义作为事务执行.

      Your recursive let from RecursiveDo is in the IO monad. The Reactive monad also has a MonadFix instance. You can define b completely within Reactive and then use a sync around this to execute the entire definition as a transaction.

      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 .

      The RecursiveDo notation isn't helping with an example this simple. The same thing can be written more easily in terms of 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)
      
          ...
      


      也许值得一提的是,通常是通过Event创建Behavior .html#v:accum"rel =" nofollow> accum .


      It's probably worth mentioning that creating a Behavior from an Event is usually done with accum.

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

      在钠中,这是一个派生函数,并且在内部根据holdsnapshotmfix进行定义.

      In sodium this is a derived function and is internally defined in terms of hold, snapshot, and 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
      

      这篇关于递归地更新“行为".钠产生的“线程阻塞..."的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆