基本知识
逻辑运算符
逻辑 | 运算符 |
---|---|
布尔值 | Ture, False |
逻辑与 | && |
逻辑或 | |
逻辑非 | not |
相等,不相等 | ==, /= |
函数
前缀函数(prefix function):大多数为前缀函数,调用时格式为:先是函数名,后跟参数列表,中间都是空格分开, 如: min 8 2
中缀函数(infix function): *就是中缀函数,夹在两个参数中间。
通过’'可以将前缀函数,转换为中缀函数:
//前缀形式
ghci> div 80 16
等价为:
//中缀形式
ghci> 80 'div' 16
列表
列表运算符
运算符 | 功能 | 例子 |
---|---|---|
++ | 拼接两个列表 | [1, 3, 5] ++ [6]=>[1, 3, 5, 6] |
: | 将元素插入表头 | [1] : [2, 3, 5, 6] => [1, 2, 3, 5, 6] |
!! | 访问列表中元素, 下标从0开始 | [1, 3, 5] !! 1 => 3 |
<,>,<=,>= | 比较两个列表大小 | [3, 2, 1] > [2, 1, 0]=>True |
列表函数
函数 | 功能 | 例子 |
---|---|---|
head | 返回列表的头部,也就是第一个元素 | head [5, 4, 3, 2, 1]=>5 |
tail | 返回列表的尾部,也就是除了头部之后的部分 | tail [5, 4, 3, 2, 1]=>[4, 3, 2, 1] |
last | 返回列表的最后一个元素 | last [5, 4, 3, 2, 1]=>1 |
init | 返回列表除了最后一个元素的部分 | init [5, 4, 3, 2, 1]=>[5, 4, 3, 2] |
length | 返回列表的长度 | length [5, 4, 3, 2, 1]=>5 |
null | 检查列表是否为空 | null [5, 4, 3, 2, 1]=>False |
reverse | 反转列表 | reverse [5, 4, 3, 2, 1]=>[1, 2, 3, 4, 5] |
take | 返回指定列表的前几个元素 | take 2 [5, 4, 3, 2, 1]=>[5, 4] |
drop | 删除指定列表的前几个元素 | drop 2 [5, 4, 3, 2, 1]=>[3, 2, 1] |
maxinum | 返回列表的最大的元素 | maxinum [5, 4, 3, 2, 1]=>5 |
mininum | 返回列表的最小的元素 | mininum [5, 4, 3, 2, 1]=>1 |
sum | 返回列表的所有元素的和 | sum [5, 4, 3, 2, 1]=>15 |
product | 返回列表的所有元素的积 | product [5, 4, 3, 2, 1]=>120 |
elem | 判断一个元素是否在列表中 | elem 4 [5, 4, 3, 2, 1]=>True |
区间
通过区间可以构造列表,其中的值必须是可枚举的,或者说,是可以排序的。
Prelude> [1..20]
[1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20]
Prelude> ['a'..'z']
"abcdefghijklmnopqrstuvwxyz"
Prelude> ['K'..'Z']
"KLMNOPQRSTUVWXYZ"
Prelude>
区间可以调整步长
Prelude> [2, 4..20]
[2,4,6,8,10,12,14,16,18,20]
Prelude> [3, 6..20]
[3,6,9,12,15,18]
为什么[2, 2…20]不行?
Prelude> [2,2..20]
[2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,22,2,2,2,2,2...
步长不是第一个数,而是通过第二个数减去第一个数计算出来的。
[2,2…20]:2-2=0, 步长成了0,一直不会到20,所以结束不了。
[20…1] 为什么为空?
ghci>[20..1]
[]
[20…1]没有提供步长,Haskell会默认构造一个空的列表,随后从区间的下限开始,不停的增长等于上限为止,20已经大于1了,所以是空。
也就是说步长默认是+1的,如果是-1,必须提供步长,[20,19…1]
ghci>[20,19..1]
[20,19,18,17,16,15,14,13,12,11,10,9,8,7,6,5,4,3,2,1]
如果不表明区间上限,将得到一个无限长度列表
ghci>[20,19..]
[20,19,18,17,16,15,14,13,12,11,10,9,8,7,6,5,4,3,2,1,0,-1,-2,-3,-4,-5,-6,-7,-8,-9,-10,-11,-12,-13,-14,-15,-16,-17,-18,-19,-20,-21,-22,-23,-24,-25,-26,-27,-28,-29,-30,-31,-32,-33,-34,-35,-36,-37,-38,-39,-40,-41,-42,-43,-44,-45,-46,-47,-48,-49,-50,-51,-52,-53,-54,-55,-56,-57,-58,-59,-60,-61,-62,-63,-64,-65,-66,-67,-68,-69,-70,-71,-72,-73,-74,-75,-76,-77,-78,-79,-80,-81,-82,-83,-84,-85,-86......
可以通过take取前几个
ghci>take 10 [20,19..]
[20,19,18,17,16,15,14,13,12,11]
另外几种生成无限列表的函数:
- cycle 函数: 接受一个列表作为参数,并返回一个无限列表
ghci>take 10 (cycle [1, 2, 3])
[1,2,3,1,2,3,1,2,3,1]
ghci>take 14 (cycle "LOL ")
"LOL LOL LOL LO"
- repeate 函数: 接受一个值作为参数,并返回一个无限列表
ghci>take 10 (repeat 6)
[6,6,6,6,6,6,6,6,6,6]
- replicate 函数: 一个参数表示列表的长度,一个参数表示要复制的值。
ghci>replicate 10 6
[6,6,6,6,6,6,6,6,6,6]
由于浮点数只能实现有限精度,最好不要在区间中使用浮点数。
ghci>[0.1, 0.2..1]
[0.1,0.2,0.30000000000000004,0.4,0.5,0.6,0.7000000000000001,0.8,0.9,1.0]
ghci>[0.1, 0.3..1]
[0.1,0.3,0.5,0.7,0.8999999999999999,1.0999999999999999]
列表推导式
列表推导式是一种过滤,转换或者组合列表的方法
ghci> [x*2 | x <- [1..10]]
[2,4,6,8,10,12,14,16,18,20]
“|” 后 x <- [1…10] : x绑定1-10每个元素
“|” 前 x*2 : 输出
还可以对绑定值增加过滤,形式为[输出 | 绑定,过滤],
如[x*2 | x <- [1…10], x > 12]
ghci> [x*2 | x <- [1..10], x*2 > 12]
[14,16,18,20]
ghci> [x*2 | x <- [1..10], x > 6]
[14,16,18,20]
将推导式设置为函数, xs是列表,绑定到x,对其中x为奇数的执行“ if x < 10 then “BOOM!” else “BANG!” ”
x <- xs, odd x 使x绑定到 7, 9, 11, 13
ghci> boomBangs xs = [ if x < 10 then "BOOM!" else "BANG!" | x <- xs, odd x]
ghci> boomBangs [7..13]
["BOOM!","BOOM!","BANG!","BANG!"]
多个列表,结果是多个表元素的组合情况
ghci> [x + y | x <- [1..5], y <- [10, 100, 1000]]
[11,101,1001,12,102,1002,13,103,1003,14,104,1004,15,105,1005]
ghci> [x * y | x <- [1..5], y <- [10, 100, 1000]]
[10,100,1000,20,200,2000,30,300,3000,40,400,4000,50,500,5000]
元组
元组: 将多个异构的值合成为一个单一值。长度固定。
长度为2的元组叫做序对(pair)
长度为3的元组叫做三元组(triple)
序对的操作:
- fst : 返回首项
- snd : 返回尾项
- zip : 通过2个列表生成序对, 2个列表不一样长时,以短的为准。
例题:
使用Haskell找出满足下列条件的三角形
- 三个表都为整数
- 三个边长度都小于等于10
- 周长为24的三角形
ghci> [(x,y,z) | x<-[1..10], y<-[1..10], z<-[1..10], x*x + y*y ==z*z, x+y+z==24]
[(6,8,10),(8,6,10)]
解题思路:先初始化集合将其变形,在通过过滤条件缩小计算范围。