开发者学堂课程【Scala 核心编程 - 进阶:作业说明和温故知新】学习笔记,与课程紧密连接,让用户快速学习知识。
课程地址:https://developer.aliyun.com/learning/course/610/detail/9102
作业说明和温故知新
内容介绍:
一、对象匹配
二、变量声明
三、样例类
四、密封类
五、作为参数的函数
六、闭包
七、抽象控制
八、使用函数式编程方式
将上次课的内容进行简短的回顾,上一次课讲的类属内容是从对象的匹配到递归。用递归的思想去思考和编程,从模式匹配的对象匹配开始到13章的函数式,编程的高级和用递归的思想去思考问题。
一.对象匹配
对象匹配,首先开篇名义讲什么是对象匹配,把概念抛出,因为类型匹配很好理解,值匹配很好理解,但是对象匹配并不是指对象相等,是指 case 中的对象的方法,提取器如果返回 some 集合则匹配成功。
如果返回 none 表示匹配失败,因此做了一些案例,如构建了一个 square ,或直接赋值也可以,当执行到 case 时,观察用什么方法来进行匹配。
在匹配时,会调unapply方法,若 unapply 方法返回的是上集合,则匹配成功,会将值放入 n 中,则 n 可用。
对象匹配后的第二个应用案例,与第一个应用案例最大的区别是如果匹配时有多个参数,会默认调用unapplySeq 的方法。其他的机制相同,另外返回的项目不是一个值,而是多个值。如返回 Alice ,交给 first ,如返回 Bob 交给 second ,如返回 Thomas 交给 third ,如果不一样,则匹配失败。
二.变量声明
变量声明中的模式。这种方式特别好用,用一条语句可以达到给多个变量赋值效果,变量定的较多时,就可以用变量声明中的模式来进行匹配,较简单,这种用法要注意。
接着讲了 For 循环表达式,体现出在 for 循环时候 ,可以根据自己的需求来取出对应的这种集合里的值,如 map ,让 k、v,就这样匹配;若只关心 map 里满足某个条件的元素,则可以指定一个固定的值进行过滤。如对条件多加一些判断,可以加首位效果更好。
三.样例类
样例类是重点,因为可以结合偏函数使用,对于它的理解,类似模板一样,因为只要声明是样例类,会默认生成一系列的方法,它除了本身实现很多方法之外,还实现了串行化的接口,串行化是把一个类型或对象经过序列化,将对象做成字符串形式,做成字符串形式的用途第一个是可以保存到文件中,即可以直接将一个对象保持到文件中,有些语言里称为 freezing 冰冻,冰冻的好处是可以使用反序列化将它再恢复,反序列化进行保存。
第二点因为对象变成字符串,可以网络上传输,这就是它的重要的作用。
若不串行化,对象就无法在网络上传输,但是 master 和 worker 进行交互时,需要进行信息传递,所以若不串行化无达到效果,而样例类默认实现了串行化。
几个最佳实践,第一个讲串行化的作用,第二个讲串行化可以拷贝等,还有中置达式,匹配嵌套模型,匹配嵌套结构当时做了一个案例,有一点小难度的,在理解的基础上能够写出,代码并不多,就一个方法即可,price怎么去用,但是要理解是如何实现的。
四.密封类
密封类是一个概念 seales ,只能在本文件使用了。紧接着讲了函数式高级编程的一部分内容。
首先是偏函数,先提出一个需求,然后用传统的方法可以解决,用模式匹配也可以解决,但是不完美。
因此解决方案本身就体现出了偏函数的本质,偏函数的本质就是先过滤再映射,但是已经提供偏函数了,就不要自己再写一遍,当时用这个方法,先 filter ,再 map 转成后再 map ,较复杂,有过滤又有映射的逻辑就是偏函数的本质。
偏函数的快速入门,先用偏函数解决前面对list的过滤并加1的操作,准确的讲偏函数就是 partialFunction 的匿名的子类,用 Defined 方法来判断是否满足调节条件,如果满足,则执行 apply 方法,如果你不满足,则不执行。
最后总结了偏函数,写先 is DefinedAt ,再写 apply ,虽然可以,但是太麻烦,因此提出了简写的形式,第一种是 case 语句,不用再分别写方法。
第二种是直接用 collect 把语句写到里面,后面学的 AKKA 也会用到偏函数这种用法,AKKA 里有个特别重要的方法叫 resive 方法,就用到了这种模式,实现偏函数的操作。
五.作为参数的函数
作为参数的函数,就是可以将函数作为一个参数传递给另外一个函数。用法也非常多,基本介绍,应用实例,代码总结。
匿名函数,是直接去声明,或定义一个匿名函数,交给一个变量,然后通过指向匿名函数的变量来对命令函数进行操作。
注意匿名函数最重要的是首先没有名字,第二个原先的等号改变且不用写返回值。
返回值用类型推导做,写上返回值会报错。高阶函数,最重要的特点有两个,第一个可以接收一个函数作为参数传入,也可以返回函数,而且函数里可以继续调用。
参数类型推断,能够实现很多简写的形式,可以让函数式编程变得更加的简洁,但是有一个前提是有应用场景,离开应用场景,就不能用了。
六.闭包
闭包,是一个函数和与其相关的引用环境构成了一个整体,换言之是有一个函数引用到外面的一个变量,而且这个变量跟函数形成了一个整体,就称为闭包 closure 。
闭包的本质很多语言里,如Python 打出直接是对象。本质仍然是一种对象的形式来管理。
如在 JavaScript 中,都有闭包的概念。闭包的价值在于,调用一个函数,但是这个函数有参数,不想反复的传递,只传递一次,这个参数就一直为我所用了,只要闭包函数没有销毁就一直可以使用。
函数柯里化( curry),是为了纪念一个数学家柯里命名的,将来会用到这种语法现象,但实际应用并不多。
举例,比较两个字符转在忽略大小写的情况下是否相等,把它拆解成两个内容,第一个转大小写,第二个判断比较,用隐式类来实现这个效果。如果只针对这一个题,这种函数柯里化意义不大,但是证明了可以通过分解参数来逐步的完成一个大的任务执法。
七.抽象控制
抽象控制,抽象控制的价值在于如果一个高阶函数,它接收的函数类型是没有输入值,也没有输出值,这种可以直接传入一段代码执行。抽象控制讲了一个应用案例是用控制抽象实现 while 语法。
八.使用函数式编程方式
使用递归的方式去思考编程,证明了速度没有影响,但有个前提,递归有一些影响的,这里的递归速度是否影响主要是递归这种机制,如果递归有重复计算,速度会有影响,因此写递归时也要考虑,如求阶乘时,fn 反复的重复计算速度会慢,但不是递归带来的。是写的问题带来的。
即写递归反复重复计算,速度一定会慢,但是不是递归的问题,是本身算法的问题。