如何将字符串转换为字符列表?

How can I convert a String into a Char list?

我正在尝试编写一个从字符串中删除特定元素的程序,但我使用的大部分内容(如 filter)仅适用于 [Char]。我真的只是不想输入 "['h','e','l','l','o']" 而不是 "hello"。我意识到从技术上讲 String 只是一个奇特的 [Char],但我如何将它取消幻想成一个标准的 [Char]。另外,如果您有另一种方式来编写普通单词而不是数组格式,请告诉我。

在Haskell中,方括号表示一个列表,在Python中也是如此。 Haskell 也使用白色 space 语法。

您可以通过在 ghci REPL 中使用 :t 来判断字符串在 Haskell 中的类型。

:t "String" -- "String" :: [Char]

所以双引号中的字符串实际上是一个字符列表。

字符串列表如何?

:t ["airplane","boat","car"] -- ["airplane","boat","car"] :: [[Char]]

所以字符串列表是字符列表的列表。

至于过滤,如果我对字符串应用过滤器,它的行为与对字符列表的过滤器完全一样:

:m +Data.Char
filter isUpper "String" -- returns "S"

如前所述,String is simply a synonym for [Char]

type String = [Char]

所以两者可以互换使用。

特别是,"hello" :: [Char]"hello" :: String完全一样,都是['h','e','l','l','o'].

更优雅的写法

也就是说,您会发现并非所有在其他语言中都是“字符串”的东西在 Haskell 中都是 String。看,列表实现实际上非常低效,尤其是在内存方面——对于 ASCII 字符串,大多数语言每个字符占用 8 位或 16 位,但对于 Haskell 的 String 类型,每个字符都是一个64 位 Char 加上对下一个字符的引用,总共 128 位!

这就是大多数现代 Haskell 库避免 String 的原因,除了像文件名这样的简短内容。 (Incidentally,

type FilePath = String

所以这也是可以互换的。)

这些库用于通用字符串的通常是 Text,这确实是一种不同的类型,更多地对应于其他语言的实现(它在底层使用 UTF-16)。

如果要过滤该类型的值,可以将其转换为带有文本库提供的 unpack, or you can simply use the dedicated version of filter 的 listy-String

在标准 Haskell 中,Text 值可以 而不是 定义为字符串或列表文字,您需要显式包装它,例如 <a href="https://hackage.haskell.org/package/text-2.0/docs/Data-Text.html#v:unpack" rel="noreferrer">pack</a> ['h','e','l','l','o']。但是,它们 仍然可以 定义为简单的字符串文字,前提是您打开 {-# LANGUAGE OverloadedStrings #-}:

ghci> :m +Data.Text
ghci> "hello" :: Text

<interactive>:5:1: error:
    • Couldn't match expected type ‘Text’ with actual type ‘[Char]’
    • In the expression: "hello" :: Text
      In an equation for ‘it’: it = "hello" :: Text

ghci> :set -XOverloadedStrings 
ghci> "hello" :: Text
"hello"

使用另一个扩展,这也适用于列表语法:

ghci> ['h','e'] :: Text

<interactive>:9:1: error:
    • Couldn't match expected type ‘Text’ with actual type ‘[Char]’
    • In the expression: ['h', 'e'] :: Text
      In an equation for ‘it’: it = ['h', 'e'] :: Text

ghci> :set -XOverloadedLists 
ghci> ['h','e'] :: Text
"he"