我正在尝试编写一个函数来检查 Haskell 中的字符串是否为回文(不区分大小写)。为了确保大写字符不会导致问题,我首先使用toLower
( https://hackage.haskell.org/package/text-2.0/docs/Data-Text.html#v:降低)。然后我检查它是否等于同一事物的反转版本。这是我的代码:
{-# LANGUAGE OverloadedStrings #-}\nimport Data.Text (toLower)\n\n\nisPalindrome :: String -> Bool\nisPalindrome xs = toLower xs == toLower $ reverse xs\n
Run Code Online (Sandbox Code Playgroud)\n我意识到toLower
使用文本而不是字符串,我们需要使用{-# LANGUAGE OverloadedStrings #-}
将字符串重载为文本。但这不能编译。
我也在 GHCI 中复制了这个。我首先用来:set -XOverloadedStrings
确保重载字符串。然后我运行这个:
Prelude Data.Text> toLower $ reverse "sdssSDSS"\n\n<interactive>:92:11: error:\n \xe2\x80\xa2 Couldn\'t match expected type \xe2\x80\x98Data.Text.Internal.Text\xe2\x80\x99\n with actual type \xe2\x80\x98[Char]\xe2\x80\x99\n \xe2\x80\xa2 In the second argument of \xe2\x80\x98($)\xe2\x80\x99, namely \xe2\x80\x98reverse "sdssSDSS"\xe2\x80\x99\n In the expression: toLower $ reverse "sdssSDSS"\n In an equation for \xe2\x80\x98it\xe2\x80\x99: it = toLower $ reverse "sdssSDSS"\n
Run Code Online (Sandbox Code Playgroud)\n我不明白为什么这不起作用。如果我第一次运行reverse "sdssSDSS"
并将结果复制粘贴到其中,toLower
则不会出现问题。
我们需要使用
{-# LANGUAGE OverloadedStrings #-}
重载String
来Text
不。该扩展名应该被称为OverloadedStringLiterals
. 它仅更改文字(例如"hello"
or )的行为"sdssSDSS"
,但不会在String
和Text
之间进行转换。一般来说,Haskell 中永远不会发生自动转换,所发生的只是您可以拥有多态值,例如具有该扩展名的数字文字或字符串文字。
在现代 Haskell 中,最好的选择可能是将其全部写入Text
并且String
根本不引入:
import qualified Data.Text as Txt
isPalindrome :: Txt.Text -> Bool
isPalindrome xs = Txt.toLower xs == Txt.toLower (Txt.reverse xs)
Run Code Online (Sandbox Code Playgroud)
(请注意,您不能使用$
There,因为它的优先级低于==
)。
但你根本不需要使用Text
,还有单字符版本toLower
:
import Data.Char (toLower)
isPalindrome :: String -> Bool
isPalindrome xs = map toLower xs == map toLower (reverse xs)
Run Code Online (Sandbox Code Playgroud)
顺便说一句,在这两种情况下都只能使用toLower
一次:
isPalindrome :: String -> Bool
isPalindrome xs = xsLC == reverse xsLC
where xsLC = map toLower xs
Run Code Online (Sandbox Code Playgroud)