let in
let in 表达式,let 中绑定的名字仅对 in 部分可见。
我们使用递归来实现斐波那契数列和快速排序,haskell写的快速排序是我见过的最容易理解的版本了,专门为解决数学问题而生的 haskell 在解决算法和数据结构方面果然是不同凡响。
-- 斐波那契数列 fab 1 = 1 fab 2 = 1 fab n = fab (n-1) + fab (n-2) -- 快速排序 quicksort [] = [] quicksort (x:xs) = let smallerSorted = quicksort [a | a <- xs, a <= x] biggerSorted = quicksort [a | a <- xs, a > x] in smallerSorted ++ [x] ++ biggerSorted尾递归实现常用的map和filter函数
[] 表示空列表
_ 匹配的是任意值。
(x:xs) 非常有用的列表匹配模式,x表示第一项,xs表示除去第一项之后的部分。使用(x:xs)可以方便的实现尾递归
-- map map' f [] = [] map' f (x:xs) = f x : map' f xs -- filter filter' _ []= [] -- _代表任意值 filter' f (x:xs) | f x = x : filter' f xs | otherwise = filter' f xs 数据类型了解了haskell基本语法后,我们再进一步了解haskell基本数据类型
:type 获取任何表达式的类型,可以用简写形式 :t
基本数据类型
Int 表示整数
Integer 也是整数,但表示的是无界的,所以可以表示非常大的数
Float 表示单精度的浮点数
Double 表示双精度的浮点数
Bool 表示布尔值,它只有两种值:True 和 False
Char 表示一个字符。一个字符由单引号括起,一组字符的 List 即为字符串
List 列表中所有的项都必须是同一类型。
Tuple 的类型取决于它的长度及其项的类型。
:t 1 -- Number 1 :: Num p => p :t 1::Integer 1::Integer :: Integer :t 1::Float 1::Float :: Float :t False -- Bool False :: Bool :t 'c' --字符 'c' :: Char :t "hello" -- 字符串 "hello" :: [Char] :t [1,2,3] -- 列表list [1,2,3] :: Num a => [a] :t [("hi",1),("there",2)] -- Tuple [("hi",1),("there",2)] :: Num b => [([Char], b)]1::Integer 表示直接指定类型,如果不指定编译器会自动推导出类型,数字类型会推导出Number类型,它包括Int,Integer,Float,Double
[Char] 和 String 表示的都是字符串类型
[1,2,3] :: Num a => [a] 列表中的 a 表示任意类型,意思你可以是Bool,Stirng,Int等等
[("hi",1),("there",2)] 这就是Tuple类型,列表里面的每个项都用 () 包起来,其中的每个项的元素数据类型必须相同,每个tuple中元素个数必须相等,但是每个tuple中的项可以不同类型,比如 ("hi",1) 中一个是字符串,一个是Int。
函数也有类型,定义函数的时候,加上参数的类型和输出类型是好习惯。
&&、||、not 表示与或非逻辑
== 表示等于
/= 表示不等于
++ 连接列表,相当于concat
a, b这种类型参数,表示可以传入任何类型。
(Num a, Num p, Ord a) => a -> p 在 => 之前表示的是类型约束,这里的 a 限定只能是 Num 类型和 Ord 类型。Num表示数字类型,Ord则表示可比较大小的型别,包含如下三种型别之一:GT, LT, EQ。
:t head -- 取列表第一项的函数 head :: [a] -> a :t sign -- sign函数 sign :: (Num a, Num p, Ord a) => a -> p :t (==) -- 是否相等 (==) :: Eq a => a -> a -> Bool :t (++) -- 列表连接函数 (++) :: [a] -> [a] -> [a] -- 执行 sign 2 > 1 head [3,2,1] > 3 "abc" == "bbc" > False "hello " ++ "world" > "hello world" List 和 List comprehension
列表常用的函数
null 列表是否为空
length 返回列表长度
head 返回列表第一个元素
tail 返回列表除第一个元素以后的所有元素
last 返回列表最后一个元素
init 返回列表除最后一个元素之前的所有元素
take n 返回列表前n个元素
drop n 丢弃列表前n个元素
maximum 返回最大的元素
minimum 返回最小的元素
sum 返回元素的和
elem 元素是否包含于列表
list range
方便的range,尾递归加上list range,你真的还需要命令式语言中的循环语句吗?