2012-01-02 248 views
3

我是Haskell的新手,并且定义了一个函数,它可以将所有小写字母转换为大写字母,并使其他字体完整无缺。将小写字母转换为大写

我想在我的书中解决这一问题至今:

capitalise :: String -> String 
capitalise xs = [capitalise2 ch| ch<-xs] 

capitalise2 :: Char -> Char 
capitalise2 ch 
    | isLower ch = chr (ord ch - 32) 
    | otherwise = ch 

我得到错误:

p3.hs:6:7: Not in scope: `isLower' 
p3.hs:6:23: Not in scope: `chr' 
p3.hs:6:28: Not in scope: `ord' 

任何帮助将非常感激。

+0

请注意,这种策略在某些语言中不起作用,因为在制作大写/小写字符时,某些字符实际上变成了更多/更少的字符。 – singpolyma 2012-09-26 14:46:47

回答

16

首先,您需要import Data.Char来使用它所抱怨的功能。

对,您在新功能中缺少otherwise个案。用if .. then .. else构造试试。有经验的Haskellers不会非常使用这个构造;我可能会用一个辅助函数做到这一点:

capitalize cs = [ toUpper c | c <- cs ] 
    where 
    toUpper ... 

这几乎是一样的你已经有了,主要区别在于辅助函数的范围。

另请参阅Data.Char.toUpper

这也可能是一个很好的机会来摆脱列表解析并开始玩高阶函数。尝试使用map而不是列表理解书写此功能。

8

本书是否解释了标准库呢?

import Data.Char (toUpper) 

capitalise = map toUpper 
+0

哎呀,我错过了导入字符。谢谢。它现在有效! – Amjad 2012-01-02 12:19:34

+7

@iPC更好'导入Data.Char'。如果你正在使用haskell98模块'Char',你不能使用'base'中的任何模块和更新的GHC。 – 2012-01-02 13:06:23

3

你需要做的,而不是使用它作为一个过滤器表达的isLower一部分。

[if isLower ch then chr (ord ch - 32) else ch | ch <- xs] 

或者,移动里面的帮助器功能。

capitalise = map capitalise' 
      where capitalise' ch 
         | isLower ch = chr (ord ch - 32) 
         | otherwise = ch 
+0

谢谢!所以我想我不会需要使用另一个功能吗?还是我? – Amjad 2012-01-02 12:21:30

+5

使用'chr','ord'和'-32'不是这样做的正确方法。使用'toUpper'。 – augustss 2012-01-02 13:20:33

+1

@augustss:这对ASCII来说已经足够了。 – 2012-01-02 14:32:06

相关问题