haskell笔记(2) - funtions

pattern matching

如果模式匹配多个值,必须用括号括起来(if you want to bind to several variables (even if one of them is just _ and doesn't actually bind at all), we have to surround them in parentheses. )

head' :: [a] -> a
head' [] = error "can head an empty list, you Dummy"
-- x:xs need to be put in parentheses
head' (x:xs) = x

模式匹配中,List直接用[x, y], [x, _]来进行匹配,不需要括号, kind of syntax sugar

tt :: (Show a) => [a] => String
tt [] = "empty list"
-- same as: tt [x] = ...
tt (x:[]) = "one element" ++ (show x)
-- same as tt [x, y] = ..
tt (x:y:[]) = "two elements" ++ (show x) ++ ", " ++ (show y)
-- can't use tt [x, y, _], may be more than 3
tt (x:y:_) = "3 or more than 3 elements"

patterns可以在匹配的同时保留整体

>>let tall all@(x:xs) = (show all) ++ ", first = " ++ show x
>> tall "554"
"\"554\""

guards

guards可以用来处理多个条件,类似于c的switch

max' :: (Ord a) => a -> a -> a  
max' a b   
    | a > b     = addOne a
    -- otherwise 处理其他
    | otherwise = b 
    where addOne x = (x+1)
              decOne x = (x-1)
-- 也可以写成一行
-- max' a b | a > b = a | otherwise = b  

可以在guards后面加where定义方法,不过where需要对齐(Notice that all the names are aligned at a single column. If we don't align them nice and proper, Haskell gets confused because then it doesn't know they're all part of the same block.)
where跟正常方法一样,可以用pattern matching, 也可以嵌套定义where

let表达式

let in , 多行bindings需要对齐,单行可以;隔开

>>(let a = 100; b = 200; c = 300 in a*b*c, let foo="Hey "; bar = "there!" in foo ++ bar) 
(6000000,"Hey there!")  

case表达式

head' :: [a] -> a  
head' [] = error "No head for empty lists!"  
head' (x:_) = x  

-- 跟上面效果一致,方法pattern match只是syntax sugar
head' xs = case xs of [] -> "No head for empty lists!"
                      (x:_) -> x
-- where 里边也可以用第一种形式
describeList :: [a] -> String
describeList xs = "The list is " ++ what xs
    where what [] = "empty."
          what [x] = "a singleton list."
          what xs = "a longer list."

常见错误

-- real world haskell
-- file: ch03/BogusPattern.hs

data Fruit = Apple | Orange
apple = "apple"
orange = "orange" 

-- apple/orange只是模式匹配的变量,不是global var=> apple/orange
whichFruit :: String -> Fruit
whichFruit f = case f of
    apple -> Apple
    orange -> Orange

-- file: ch03/BogusPattern.hs
equational apple = Apple
equational orange = Orange

-- file: ch03/BogusPattern.hs
betterFruit f = case f of
"apple" -> Apple
"orange" -> Orange

pattern match不能多次用同一个变量表示匹配变量相同(A name can appear only once in a set of pattern bindings)

bad_nodesAreSame (Node a _ _) (Node a _ _) = Just a

你可能感兴趣的:(haskell笔记(2) - funtions)