gpt4 book ai didi

haskell - 编写函数 (a -> b -> ... -> t) -> (Monad m => m a -> m b -> ... -> m t)

转载 作者:行者123 更新时间:2023-12-02 16:25:27 27 4
gpt4 key购买 nike

有没有办法写一个函数f::(a -> b -> ... -> t) -> (Monad m => m a -> m b -> ... -> m t ),基本上是 liftMn 对于任何 n

(编辑:修复了无意义的示例。)

我正在编写一个 FRP 库,并且认为如果我能有模糊的代码,那就太好了:

main = do
input1 <- signalFromTextBoxTheUserMayTypeANumberInto
input2 <- signalFromAnotherTextBox
divided <- signal div input1 input2
signal (\x -> showTextAlert ("input1 `div` input2 is " ++ show x)) divided

我一直在摆弄类型系列以使其正常工作,但我开始认为这实际上是不可行的。我目前正在做这样的事情:

type Action a = IORef a -> IO ()
type Listener = IO ()
newtype Signal a = Signal (IORef (SigData a))

data SigData a = SigData {
trigger :: Action a,
output :: IORef a,
listeners :: [Listener]
}

class Sig a where
type S a
mkSig :: [AnySignal] -> a -> S a

instance Sig b => Sig (a -> b) where
type S (a -> b) = Signal a -> S b
mkSig dependencies f =
\s@(Signal sig) ->
let x = unsafePerformIO $ readIORef sig >>= readIORef . output
in mkSig (AnySignal s : dependencies) (f x)

instance Sig Int where
type S Int = IO (Signal Int)
out <- newIORef x
self <- Signal <$> (newIORef $ SigData {
trigger = \ref -> writeIORef ref $! x,
output = out,
listeners = []
})
mapM_ (self `listensTo`) deps
return self

这显然不起作用,因为 unsafePerformIO 会被评估一次,然后保留该值,即使起作用,它仍然是丑陋的、黑客的并且通常是邪恶的。有没有办法做到这一点,还是我必须放弃这个想法?

最佳答案

我对这一切都很陌生,所以如果这是一个愚蠢的答案,请原谅我,但这不正是应用仿函数的用途吗?

应用程序可让您执行以下操作:

f :: a -> b -> ... -> c

f2 :: Applicative p => p a -> p b ... -> p c
f2 x ... y = f <$> x <*> ... <*> y

如果我没记错的话。 (省略号是任意数量的类型/参数)

关于haskell - 编写函数 (a -> b -> ... -> t) -> (Monad m => m a -> m b -> ... -> m t),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9828401/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com