我正在尝试在 Haskell 中的字符串末尾添加一个字符串。
albumStr = ""
main = do
let albumStr = albumStr ++ "nothing"
print albumStr
每当我运行它时,它都会卡住"在控制台中,我必须终止它。
为什么?我如何以这种方式将一个字符串添加到另一个字符串?
编辑:如何在当前字符串的末尾添加多个字符串而不覆盖它。
谢谢
与ML不同,Haskell没有rec
关键字来标记递归定义。相反,所有定义都可以是递归的,这意味着在每个变量定义中,定义的变量在其定义过程中已经在范围内。
所以在let albumStr = albumStr ++ "nothing"
中,=
右侧的albumStr
是指=
左侧定义的,而不是第1行中定义的那个。因此,定义是无限递归的,并且永远循环。
如果要基于另一个变量定义变量,则必须为其指定不同的名称:
let localAlbumStr = albumStr ++ "nothing"
等式
albumStr = albumStr ++ "nothing"
递归定义字符串,并且根本不使用全局定义的albumStr
。递归立即挂起(它类似于无限循环(。
打开警告会报告全局名称的阴影。
如果不需要递归定义,请使用另一个变量名称:
albumStr2 = albumStr ++ "nothing"
在do
表示法中,你可以写
do { albumStr <- pure (albumStr ++ "nothing")
; ...
}
它(似乎(会起作用。
虽然Haskell中的let
(和函数(绑定是递归的,但do
绑定不是。
相反,会自动创建一个阴影变量,它实际上是一个具有相同名称的新变量。<-
右侧的代码位于绑定上方的作用域中;<-
左侧的代码位于一个新的、更广泛的范围内(包括较早的范围(。
另请参阅:
- 如何在函数式编程中递增变量