显然唯一可能的解释runSomeMonad do ...是runSomeMonad (do ...).为什么不是Haskell语法允许的第一个变体?有些情况foo do bar可能实际上是模棱两可的吗?
当我正在学习Haskell时,我意识到do符号只是合成糖:
a = do x <- [3..4]
[1..2]
return (x, 42)
Run Code Online (Sandbox Code Playgroud)
翻译成
a = [3..4] >>= (\x -> [1..2] >>= (\_ -> return (x, 42)))
Run Code Online (Sandbox Code Playgroud)
我意识到我可能会使用do-notation,但我想了解翻译中发生的事情.纯粹出于教学原因,ghc/ghci有没有办法给我一个用do-notation编写的相当复杂的monad的相应绑定语句?
编辑.事实证明#haskell上的lambdabot可以做到这一点:
<Guest61347> @undo do x <- [3..4] ; [1..2] ; return (x, 42)
<lambdabot> [3 .. 4] >>= \ x -> [1 .. 2] >> return (x, 42)
Run Code Online (Sandbox Code Playgroud)
这是Undo插件的源代码.
嗯,问题是自我解释.假设我想实现一些特殊的语法只是为了好玩.可能吗?我应该使用什么工具?
我正在努力掌握State Monad并且为了这个目的,我想编写一个使用线性同余生成器生成一系列随机数的monadic代码(可能不好,但我的目的只是学习State Monad,而不是建立一个好的RNG库).
生成器就是这样(Bool为了简单起见,我想生成一系列s):
type Seed = Int
random :: Seed -> (Bool, Seed)
random seed = let (a, c, m) = (1664525, 1013904223, 2^32) -- some params for the LCG
seed' = (a*seed + c) `mod` m
in (even seed', seed') -- return True/False if seed' is even/odd
Run Code Online (Sandbox Code Playgroud)
不要担心数字,这只是种子的更新规则(根据Numerical Recipes)应该生成Ints 的伪随机序列.现在,如果我想按顺序生成随机数,我会这样做:
rand3Bools :: Seed -> ([Bool], Seed)
rand3Bools seed0 = let (b1, seed1) = random seed0
(b2, seed2) = random seed1
(b3, seed3) = random …Run Code Online (Sandbox Code Playgroud) 在Haskell do-notation块中说,我希望有一个变量来is_root指示我是否是root:
import System.Posix.User
main = do
uid <- getRealUserID
is_root <- return $ uid == 0
Run Code Online (Sandbox Code Playgroud)
那个讨厌的uid变量只用在那个地方.我希望我可以这样写:
main = do
is_root <- getRealUserID == 0
Run Code Online (Sandbox Code Playgroud)
但当然不会编译.
我怎样才能摆脱多余的变量uid呢?这是我提出的最好的:
import System.Posix.User
main = do
is_root <- getRealUserID >>= return . ((==) 0)
Run Code Online (Sandbox Code Playgroud)
布莱什!有更好的方法吗?
我无法弄清楚如何制作简明的if-then-else表示法,请参阅[ http://hackage.haskell.org/trac/haskell-prime/wiki/DoAndIfThenElse ].这有效,
import System.Environment
main = do
args <- getArgs
if (args !! 0) == "hello"
then
print "hello"
else
print "goodbye"
Run Code Online (Sandbox Code Playgroud)
但这不,并且插入所述分号(请参阅链接)只会导致我的解析错误.
import System.Environment
main = do
args <- getArgs
if (args !! 0) == "hello" then
print "hello"
else
print "goodbye"
Run Code Online (Sandbox Code Playgroud) 以下代码非常清楚:
do
x <- Just 3
y <- Just "!"
Just (show x ++ y)
Run Code Online (Sandbox Code Playgroud)
这里的类型x是Num和y是String.(<-这里用来取出Monad的实际价值)
但是,这个片段对我来说不太清楚:
import Control.Monad.Instances
addStuff :: Int -> Int
addStuff = do
a <- (* 2)
b <- (+ 10)
return (a + b)
Run Code Online (Sandbox Code Playgroud)
这里有什么类型a和类型b?他们似乎像一个Num,但a <- (* 2)和b <- (+ 10)这里看上去很神秘,...
有没有人有这个想法?
我将协程实现从Control.Monad.CoroutineJavascript 翻译过来。翻译可能包含一些错误,但我的实际问题是我不知道如何将所有内容放在一起来应用它。
原始协程类型是m (Either (s (Coroutine s m r)) r),其中m有一个 monad 和s一个函子约束:
-- | Suspending, resumable monadic computations.
newtype Coroutine s m r = Coroutine {
-- | Run the next step of a `Coroutine` computation.
-- The result of the step execution will be either a suspension or
-- the final coroutine result.
resume :: m (Either (s (Coroutine s m r)) r)
}
instance (Functor s, Monad m) => Monad …Run Code Online (Sandbox Code Playgroud) javascript monads functional-programming coroutine do-notation
我试图在哈斯克尔去做一个do语句.我在这里找到了一些例子但是不能将它们应用到我的案例中.我唯一能想到的是一个沉重的嵌套let语句,看起来很难看.
应该用bind替换表示法的语句:
do num <- numberNode x
nt1 <- numberTree t1
nt2 <- numberTree t2
return (Node num nt1 nt2)
Run Code Online (Sandbox Code Playgroud)
任何输入都高度赞赏=)
我有一系列网络请求,每个请求大于10秒.
为了让用户知道发生了什么,我给出了更新:
main = do putStr "Downloading the first thing... "
{- Net request -}
putStrLn "DONE"
putStr "Downloading the second thing... "
{- Net request -}
putStrLn "DONE"
Run Code Online (Sandbox Code Playgroud)
使用GHCi,这可以按预期工作,但编译或使用runghc,"下载"不打印直到"完成".
我用(>> =)和(>>)重写了它,但是我遇到了同样的问题.
这是怎么回事?