当前位置:  开发笔记 > 编程语言 > 正文

问题与Haskell的"做"

如何解决《问题与Haskell的"做"》经验,为你挑选了2个好方法。

我编写了一个Haskell函数,用于计算给定列表中每个数字的阶乘,并将其打印到屏幕上.

factPrint list =
if null list
    then putStrLn ""
    else do putStrLn ((show.fact.head) list)
        factPrint (tail list)

该功能有效,但我发现第三行有点令人困惑.为什么编译器(GHC)没有报告错误,因为在"putStrLn"(准?)函数之前没有"do"?如果我从第4行省略"do",则会按预期弹出错误.

我对Haskell及其方式都很陌生,所以如果我说的话过于愚蠢,请原谅我.



1> newacct..:
do putStrLn ((show.fact.head) list)
   factPrint (tail list)

实际上是另一种写作方式

putStrLn ((show.fact.head) list) >> factPrint (tail list)

反过来,这意味着

putStrLn ((show.fact.head) list) >>= \_ -> factPrint (tail list)

do符号串是这些单子在一起,如果没有这个丑陋的其他语法的便捷方式.

如果你里面只有一个语句do,那么你就不会把任何东西串在一起,这do是多余的.



2> Nathan Shive..:

如果您是Haskell的新手,请考虑使用do类似ifC语言的类似于必需的大括号:

if (condition)
  printf("a"); // braces not required
else {
  printf("b"); // braces required
  finish();
}

do 在Haskell中以相同的方式工作.


也许有助于查看factPrint的类型,然后重构使用模式匹配:

factPrint :: [Int] -> IO ()
factPrint [] = putStrLn ""
factPrint list = do
  putStrLn (show.fact.head) list
  factPrint (tail list)

所以,如果factPrint返回IO (),和类型putStrLn ""IS IO (),那么它是完全合法的factPrint []平等putStrLn "".没有do必要 - 事实上,你可以说,factPrint [] = return ()如果你不想要尾随换行符.

推荐阅读
大大炮
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有