首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >专栏 >Haskell 基础

Haskell 基础

作者头像
Orlion
发布于 2024-09-02 08:17:47
发布于 2024-09-02 08:17:47
21900
代码可运行
举报
文章被收录于专栏:我的独立博客我的独立博客
运行总次数:0
代码可运行

第一个函数

创建doubleMe.hs文件,编写如下代码:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
doubleMe x = x + x

保存,打开ghci,输入

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
Prelude> :l doubleMe.hs

这样我们就加载了我们的doubleMe函数,然后就可以调用这个函数:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
Prelude> doubleMe 10
20

tip: 如果修改doubleMe.hs文件需要重新导入的话可以执行:reload doubleMe.hs或者:r doubleMe.hs重新导入

if语句

Haskell中的if语句与其他语言不同,else是不可以省略的

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
doubleSmallNum x = if x > 10 then x else x * 2

Haskell 中的 if 语句的另一个特点就是它其实是个表达式,表达式就是返回一个值的一段代码:5 是个表达式,它返回 5;4+8 是个表达式;x+y 也是个表达式,它返回 x+y 的结果。正由于 else 是强制的,if 语句一定会返回某个值,所以说 if 语句也是个表达式。

List

列表由方括号以及被逗号间隔的元素组成:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
Prelude> [1,2,3]
[1,2,3]

空列表:[],列表中所有元素必须是同一类型。

列表操作符

用 ++ 操作符连接两个list

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
Prelude> [1,2,3] ++ [4,5,6]
[1,2,3,4,5,6]

用 : 连接一个元素到list头,它读作“cons”即construct简称

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
Prelude> 1:[2,3]
[1,2,3]

但是[2,3]:1是不被允许的,因为:的第一个参数必须是单个元素,第二个参数必须是list

字符与字符串

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
Prelude> "this is string"
this is string

双引号表示字符串。单个字符用”表示

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
Prelude> 't'
t

字符串实际是字符列表,

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
Prelude> 't' : "his is string"
this is string
Prelude> "this is" ++ " string"
this is string

操作

从list中取值使用!!(相当于其他语言中的arr[index])

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
Prelude> let l = [1,2,3]
Prelude> l!!1
2

上面的例子就是从列表l中取下标为1的元素 list可以用来装list:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
Prelude> let l = [[1,2,3], [1,2,3,4], [1,2,3,4,5]]

haskell不要求每个元素的长度一致,但要求类型必须一致

  • head函数取list第一个元素
  • tail函数取list除第一个元素之后的全部
  • last返回list最后一个元素
  • init返回一个除去list最后一个元素的全部
  • length返回list长度
  • null判断list是否为空,如果是空返回True,否则False
  • reverse 反转list
  • take 返回前几个元素
  • maximum 返回最大元素
  • minimun 返回最小元素
  • sum 返回所有元素之和,product返回积
  • elem 判断一个元素是否存在于list中,通常中缀调用 Prelude> tail [[1,2,3], [1,2,3,4], [1,2,3,4,5]] [[1,2,3,4], [1,2,3,4,5]] Prelude> init [[1,2,3], [1,2,3,4], [1,2,3,4,5]] [[1,2,3], [1,2,3,4]] Prelude> reverse [1,2,3] [3,2,1] Prelude> take 2 [1,2,3] [1,2] Prelude> 1 `elem` [1,2,3] True

Range

可以用列表符号来表示一系列元素,haskell会自动推导:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
Prelude> [1..10]
[1,2,3,4,5,6,7,8,9,10]

Prelude> [1.0, 1.25, ..2.0]
[1.0,1.25,1.5,1.75,2.0]

Prelude> [1, 4, 15]
[1, 4, 7, 10, 13]

之所以没有输出15是因为15不属于我们定义的系列元素

List Comprehension

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
Prelude> [x*2 | x <- [1...10]]
[2,4,6,8,10,12,14,16,18,20]

可以给这个comprehension加个限制条件:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
Prelude> [x*2 | x <- [1...10], x*2 > 12]
[14,16,18,20]

下面写一个函数,该函数使list中所有>10的奇数变为”BANG”,小于10的奇数变为BOOM:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
bangBoom xs = [if x > 10 then "BANG" else "BOOM" | x <- xs, odd x]

tip: odd函数判读x是否是奇数,如果是则返回True

还可以从多个list中取元素:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
[x*y | x <- [1,2,3], y <- [4,5,6]]
[4,5,6,8,10,12,12,15,18]

实现自己的length函数:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
length' xs = sum [1 | _ <- xs]

_表示我们不会用到这个值 操作含有 List 的 List

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
Prelude> let xxs = [[1,3,5,2,3,1,2,4,5],[1,2,3,4,5,6,7,8,9],[1,2,4,2,1,6,3,1,3,2,3,6]]
Prelude> [ [ x | x <- xs, even x ] | xs <- xxs]
[[2,2,4],[2,4,6,8],[2,4,2,6,2,6]]

Tuple

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
(1,2)      (True, "a", 1)

Tuple List:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
[(1,2),(3,4),(5,6)]

但是[(1,2),(3,4,5),(5,6)]是会报错的,因为元素类型不一致 两个元素的Tuple可以称为序对(Pair) Tuple不能是单元素的,因为没有意义

操作函数

fst 返回序对的首项(只能操作序对,不能操作三元组等其他数量的Tuple)

snd 返回序对的尾项

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
Prudule> fst (1,2,[1,2,3])
1
Prudule> snd (1,2,[1,2,3])
[1,2,3]

zip 将两个list交叉配对生成一组Pair

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
Prudule> zip [1 .. 5] ["one", "two", "three", "four", "five"]
[(1,"one"),(2,"two"),(3,"three"),(4,"four"),(5,"five")]
Prudule> zip [5,3,2,6,2,7,2,5,4,6,6] ["im","a","turtle"]
[(5,"im"),(3,"a"),(2,"turtle")]

若是两个不同长度的 List,较长的那个会在中间断开,去匹配较短的那个

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2019-12-25,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
暂无评论
推荐阅读
编辑精选文章
换一批
基础语法_Haskell笔记1
Haskell是一种纯函数式语言(purely functional programming language),其函数式特性的纯度没有争议
ayqy贾杰
2019/06/12
2.3K0
learn-haskell
引言 Haskell不同于Scala,是一门纯函数式语言,它强制使用者使用函数式语法而没有妥协。 是一门强类型定义的静态类型语言。它的**类型模型基于推断理论(in-ferred)**并被公认为是函数语言中最高效的类型系统之一。你会发现该类型系统支持多态语义并有助于人们作出十分整洁清晰的设计。 支持Erlang风格的模式匹配(pattern matching)和哨兵表达式。你也能在Haskell中发现Clojure风格的惰性求值(lazyevaluation)以及与Clojure和Erlang相同的列表推导
刘笑江
2018/05/28
1.3K0
Haskell Type与Typeclass
我们可以这样解读这个函数的类型:removeNonUppercase这个函数接收一个Char List类型的参数返回一个Char List类型的返回值
Orlion
2024/09/02
2310
Haskell 函数语法
guard由跟在函数名及参数后边的竖线标志,通常竖线都是靠右一个缩进排成一列。一个guard就是一个布尔表达式,如果是True,就使用对应的函数体。最后的一个guard往往是otherwise,它的定义就是简单一个otherwise = True。
Orlion
2024/09/02
1950
热爱函数式的你,句句纯正的 Haskell【类型篇】
---- theme: github 每次看到干尸鬼鲛起舞,都有一种说不出的难受,不行,发出来,让大家一起难受难受~🐶 Haskell 是一门纯的函数式语言。 也就是说计算机主要是通过函数来完成的(像在数学中一样),而不是通过“先做这个,再做那个”的命令式操作顺序进行的(像在主流的编程语言中一样)。—— Simon Peyton Jones 初见😀 什么是 Haskell ?我们从 wiki 上可以找到以下要点: Haskell 是一种标准化的,通用的纯函数式编程语言,有惰性求值和强静态类型; 在H
掘金安东尼
2022/09/19
1.4K0
热爱函数式的你,句句纯正的 Haskell【类型篇】
热爱函数式的你,句句纯正的 Haskell【库函数篇】
本篇是笔记篇,介绍 Haskell 的强大的库函数,也可感受下与我们平常的 js 操作异同之处:
掘金安东尼
2022/09/19
5500
让Monad来得更猛烈些吧_Haskell笔记11
最早接触过IO Monad,后来又了解了Maybe Monad和List Monad,实际上还有很多Monad(比如Writer Monad、Reader Monad、State Monad等),位于mtl package,可以通过ghc-pkg命令来查看:
ayqy贾杰
2019/06/12
1.7K0
从 Java 和 JavaScript 来学习 Haskell 和 Groovy(DSL)
这是《从 Java 和 JavaScript 来学习 Haskell 和 Groovy》系列的第四篇。
四火
2022/07/19
6270
从 Java 和 JavaScript 来学习 Haskell 和 Groovy(DSL)
Python list列表
1,列表是由一系列元素组成,元素与元素之间可能没有任何的关联关系,但他们之间有先后顺序关系。
py3study
2020/01/10
9470
Python基础之公共方法
python3中取消了cmp比较运算符,但我们可以直接通过比较运算符<>进行比较; 数字可以比较,字符串可以比较,元组,列表可以比较大小,但字典不能比较大小
py3study
2020/01/15
8360
python3--列表推导式,生成器表达式,内置函数
3,python不但使用迭代器协议,让for循环变得更加通用,大部分内置函数,也是使用迭代器协议访问对象的,例如sum函数是python的内置函数,该函数使用迭代器协议访问对象,而生成器实现了迭代器协议,所以,我们可以直接这样计算一系列值的和
py3study
2018/08/02
2.5K0
热爱函数式的你,句句纯正的 Haskell【表达式篇】
表达式是编程语言中最常用到的基础之一,本片让我们来看看在 Haskell 中表达式是怎样的?
掘金安东尼
2022/09/19
1.2K0
热爱函数式的你,句句纯正的 Haskell【表达式篇】
从惰性IO说起_Haskell笔记6
从硬盘读文件时并不会一次性全读入内存,而是一点一点的流式读取。文本文件的话,默认buffer是line-buffering,即一次读一行,二进制文件的话,默认buffer是block-buffering,一次读一个chunk,其具体大小取决于操作系统
ayqy贾杰
2019/06/12
2.5K0
Python3学习笔记 | 十二、Python的语句与语法-赋值与表达式
在Python里,赋值语句与其它语言有所不同,它不是直接把相应的值赋给变量,而是把对象的地址赋给变量,让变量可以找到相应的对象,这个叫做对象的引用。 • 赋值语句建立对象引用值。Python赋值可以理解成存储了对象的指针 • 变量名在首次赋值时会被创建。因为变量本身没有类型,所以不需要提前创建 • 变量名在引用前必须先赋值。 • 执行隐式赋值的一些操作。所谓的隐式赋值,就是函数调用、模块倒入、类的定义、for 循环等。
TeamsSix
2019/09/24
9740
newtype_Haskell笔记8
在List场景,xs <*> ys表示从左侧xs中取出函数作用于右侧ys中的每一项,有两种实现方式:
ayqy贾杰
2019/06/12
7950
Python基础(4)——数组&元组
以中括号([])表示,每个元素以逗号隔开,里面可以存放相同的数据类型也可以存放不同的数据类型。
羊羽shine
2019/05/28
1.6K0
python基础教程:元组
元组(元组)跟列表(名单)非常相似,二者之间的差异就是元组不可改变,列表是可以改变的。
一墨编程学习
2019/05/15
8710
Python学习笔记整理(十一)pyth
while语句,提供了编写通用循环的一种方法,而for语句是用来遍历序列对象内的元素,并对每个元素运行一个代码块。break,continue用在循环内,跳出整个循环或者跳出一次循环。 一、while循环 1、一般格式 格式:首行以及测试表达式,有一列或多列缩进语句的主体以及一个选用的else部分(控制权离开循环时而没有碰到break语句时会执行) python会一直计算开投的测试,然后执行循环主体内的语句,直到测试返回假值为止。 while <test>:     <statements1> else:     <statements2> 2、例子 >>> while True: ...  print "Type Ctrl+C to stop!" >>> while x:    ...     print x, ...     x=x[1:] ... diege iege ege ge e 注意 print末尾的逗号,会使所有输出都出现在同一行。 >>> a,b=0,10 >>> while a<b: ...     print a, ...     a+=1 ... 0 1 2 3 4 5 6 7 8 9 Python并没有其他语言中所谓的"do until”循环语句,不过我们可以在循环主体底部以一个测试和break来实现类似的功能。 while    True:     do something     if exitTest():break 3、对比shell的while语句 while 命令 do     命令1     命令2 done 在系统管理时常用与逐行读取一个文件并处理。 while read line do         echo $line done < /etc/rc.conf shell中还有一个类似while的循环until until 条件 do         命令1         命令2 done EG: IS_ROOT=`who |grep root` until [ "$IS_ROOT" ] do         echo 'root online'         sleep 2 done             二、 break continue pass和循环的else break     跳出最近所在的循环(跳出整个循环语句) continue     跳到最近所在循环的开头处(来到循环的首行,跳过本次循环) pass     什么事也不做,只是空占位语句 循环else块     只有当循环正常离开时才会执行(也就是没有碰到break语句) 1、一般循环格式 加入break和continue语句后,while循环的一般格式如下: while <test>:     <statements1>     if <test2>:break     if <test3>:continue     if <test4>:pass else:     <statements2> break和continue可以出现在while(或for)循环主体的任何地方,但通常会进一步嵌套在if语句中,根据某些条件来采取对应的操作。 2、列子 pass >>> while 1:pass ... pass可用于空类,有时有指的是"以后会填上”,只是暂时用于填充函数主体而已: >>> def func1(): ...     pass continue continue语句会立即跳到循环的顶端,开始下一次循环。 >>> while x: ...     x=x-1 ...     if  x%2!=0:continue ...     print x, ... 8 6 4 2 0 这个例子中,如果是奇数就返回循环顶部,不会打印.是偶数就打印。 这个下面这个结果一样 >>> while x:            ...     x=x-1           ...     if x%2==0:      ...             print x, ... 8 6 4 2 0 注意这两个例子的print位置,第一个print是属于while块的,测试不通过下执行,测试通过就回到循环顶端,第二个是属于if块的,只有测试通过才打印 >>> while x:            ...     x=x-1           ...     if x%2==0:      ...             print x, ...break break语句会
py3study
2020/01/07
1.1K0
python中创建集合的语句_Python 集合(set) 介绍
#1.经理有:曹操,刘备,孙权#技术员有:曹操,孙权,张飞, 关羽#用集合求:#1. 即是经理也是技术员的有谁?#2. 是经理,但不是技术人员的都有谁?#3. 是技术人员,但不是经理的人都有谁?#4. 张飞是经理吗?#5. 身兼一职的人都有谁?#6. 经理和技术人员共有几个人?
用户7886150
2021/01/26
1.9K0
1.Python3基础入门学习笔记(一)
在Linux中安装Python3命令,在官网下载 https://www.python.org/downloads/source/
全栈工程师修炼指南
2022/09/28
1.1K0
1.Python3基础入门学习笔记(一)
相关推荐
基础语法_Haskell笔记1
更多 >
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档