第五课:零基础实战函数式编程
package com.dt.spark.scala.basics
/**
* 函数是可以被简单地认为一条或者几条语句的代码体,该代码接收若干参数,经过代码处理后返回结果
* 例如形如数学中的f(x)=x+1,在Scala中,函数是一等公民,可以像变量一样被传递,被赋值,
* 同时函数可以赋值给变量,也可以赋值给函数,之所以可以是这样,原因在于函数背后是类和对象!!!
* 也就是说在运行的时候,函数其实一个变量!!当然,这背后的类的Scala语言自动帮助我们生成的,
* 且可以天然地被序列化和反序列化,这个意义非常重大 :
* 1.可以天然地序列化和反序列化的直接好处是函数可以直接在分布式系统上传递
* 2.因为函数背后是类和对象,所以可以跟普通的变量完全一样地应用在任何普通变量应用的地方
* 包括作为参数传递,作为返回值,被变量赋值,和赋值给变量等
*
*
* 补充:整个IT编程技术的发展史,就是一部封装史,就像在Function时代C语言中提供了函数的概念
* 在Class时代C++和Java等语言中,提供了类和对象,把数据和处理数据的业务逻辑封装起来
* 在framework时代,把数据,代码,驱动引擎封装起来,是过去十年和未来十年的IT核心
*
* 关于函数入门的几个要点:
* 1.def 定义函数
* 2.函数会自动进行类型推导来确定函数的返回值类型,如果函数名称和函数体之间没有等号,则类型推导失败,此时函数的类型是Unit
* 3.函数的参数可以是函数
* 4.如果在函数体中无法推导出函数的类型,则必须声明类型,例如fab
* 5.函数的参数可以有默认值,这样在调用函数的时候,如果不想改变默认值的话,就直接不传递该参数,而是直接使用默认值就可以,这在实际的编程中意义重大,
* 尤其在Spark等框架中,因为框架一般都有自己的默认实现,这样我们可以很好地使用默认值
* 6.我们可以基于函数的参数的名称来调整函数传递参数的顺序,重点在于为什么可以这么做?
* 原因在于函数的背后其实是类,参数其实就是类的成员,所以无所谓顺序
* 7.函数如果不确定参数的个数,可以使用变长参数的方式,传参数的时候一个方便的语法是: _*
* 8.可变参数中的数据其实会被收集成为数组,我们在入口方法main中其实就是可变参数
* 以Array[String] 的方式呈现的
*
*/
object HelloFunctionPrograming {
def main(args:Array[String]){
println(hello("Spark",6))
println(fab(10))
hello("Scala")
hello(age=20,name="spark")
println(sum(1,2,3,4,5))
println(sum(1 to 5 : _*))
println(sumRe(1 to 5 : _*))
}
def hello(name:String,age:Int = 10) = {
println("Hello,"+name)
println("age is"+age)
age
}
def fab(n:Long): Long = {
if(n<=1) 1
else fab(n-1)+fab(n-2)
}
def sum(numbers:Int*):Int={
var sum:Int=0
for(num <- numbers){
sum = sum + num
}
sum
}
def sumRe(numbers:Int*):Int={
val len=numbers.length
if(len==1) numbers(0)
else {
var sum=numbers.head
sum = sum + sumRe(numbers.tail : _*)
sum
}
}
}
归纳总结:1.在Scala中,函数是什么?背后的原因是什么?意义在于什么?
2.了解整个IT编程技术的发展史
3.关于函数入门的几个要点
4.关于函数的参数的默认值
5.关于函数参数的顺序
6.关于变长参数的使用
转载于:https://my.oschina.net/u/1449867/blog/719848