(三)Scala从入门到项目实战(Flink、Spark、Kafka)——Scala方法和函数

目录

方法和函数

方法的定义

递归方法

方法的默认参数

可变参数的方法

嵌套方法

匿名函数

偏应用函数

高阶函数

方法的参数是函数

方法的返回是函数

方法的参数和返回都是函数

柯里化函数


方法和函数

说明:在Scala中既有方法也有函数,大多数情况下,他们没有区别,作为初学者暂时不用明确区分。一般情况下方法的类型为具体一个返回值类型,可以省略不写。而函数的类型为:参数类型 => 返回值类型 ,也可以省略不写,在后边的代码中会体现这个特点。

方法的定义

    def max(a:Int,b:Int):Int={

      if(a>b) return a else return b

    }

    println(max(1, 3))

 

                     

  1. 方法用def来定义
  2. 方法体中最后的返回值可以使用return,如果使用了return,那么方法体的返回值类型一定要定义
  3. 如果方法体中没有return,默认将方法体中的最后一行计算的结果当做返回值返回,方法体的返回值类型可以省略(自动推断)
  4. 定义方法传入的参数一定要指定类型
  5. 如果方法体为一行代码,方法的定义也可以简写

比如:

    def max(a: Int, b: Int): Int = if (a > b) return a else return b
  • 如果定义的方法没有返回值(Unit)也可以省略方法名称和方法体之间的“=”,要注意,省略了等号,不管有没有返回值都不会反回任何内容。

递归方法

定义方法递归调用时必须显示的定义出函数返回值,否则其无法推断,不能通过编译

  def fun(num: Int): Int = {

    if (num == 1) 1 else num * fun(num - 1)

  }

方法的默认参数

Scala支持定义方法时对参数设置默认值。调用时输入参数则使用输入的参数,空参则使用默认值

  def sum(a: Int = 10, b: Int = 20) = {

    a + b

  }

  println(sum())//空参

  println(sum(100,200))//覆盖

  println(sum(100))//覆盖a

  println(sum(b=200))//覆盖b

 

可变参数的方法

与java相同,scala同样有参数可变的需求

  def sum(num: Int*): Int ={ // * 号代表此参数可以有多个,但是传入的值类型必须相同。

    var sum = 0

    for(i <- num){

      sum += i

    }

    sum

  }

嵌套方法

  方法的嵌套类似if、for的嵌套,以下列子为:求5的阶乘。

  def fun1(num:Int): Int ={

    def fun2(a:Int,b:Int): Int ={

      if(a==1){

        b

      }else{

        fun2(a-1,a*b)

      }

    }

    fun2(num,1)

  }

匿名函数

匿名函数定义方法如下,一般在作为参数传入其他方法或函数中只使用一次的情况中使用,类似java中的匿名内部类。

 (a:String) => {

    println(a)

  }

当然匿名函数也可以有引用

  val stringToUnit: String => Unit = (a: String) => {

    println(a)

  }

stringToUnit("Dongcc")

偏应用函数

偏应用函数一般用来解决一个方法中的参数非常多,并且有部分参数总是不发生变化(比如下面第一段代码中,“现在是”这个参数每次都不需要变化)而每次调用这个方法总是需要传入这些不变的参数的问题。此时可以使用偏应用函数来简化这个过程(见第二段代码)。

  def showDate(s:String,date:Date): Unit ={

    println(s"$s : $date")

  }

  showDate("现在是",new Date())

  Thread.sleep(1000)

  showDate("现在是",new Date())

  Thread.sleep(1000)

  showDate("现在是",new Date())

 

为showDate方法定义偏应用函数showDate2

  val showDate2: Date => Unit = showDate("现在是", _: Date)

  showDate2(new Date())

高阶函数

在高阶函数中,有三种表现形式

方法的参数是函数

 

 def fun(f:(Int,Int)=>Int,s:String): Unit ={

    val i = f(100, 2)

    println(s"100 和 2 的 $s 是 $i")

  }

  //这里传入一个匿名函数作为参数

  fun((a:Int,b:Int)=>{a+b},"和")

方法的返回是函数

这里用一个场景说明以下代码,假设有这样一个场景,我们需要按照用户的不同情况来决定下一步应该使用什么样的函数,比如以下代码表示的是当输入年龄信息为18岁以下时,返回不可参加工作的函数,而18岁及以上时返回可以参加工作的函数。

返回的函数也可以是匿名函数,return可以省略不写,新版本中fun方法的返回值类型也可以不写。

 

   def fun(a: Int): (String) => Unit = {

    if (a >= 18) {

      def fun1: String => Unit = (s: String) => {

        println(s"$s 成年了,可以参加工作了")

      }


      return fun1

    } else {

      def fun2: String => Unit = (s: String) => {

        println(s"$s 未成年,不可以参加工作")

      }


      return fun2

    }

  }



  val fun1: String => Unit = fun(13)

  fun1("锤锤")

  val fun2: String => Unit = fun(22)

  fun2("铁蛋")

  //因为返回值是一个函数,所以也可以直接调用返回值

  fun(18)("Dongcc")

注意:在2.10版本之前,方法的返回值类型应该显示声明

 

                         

方法的参数和返回都是函数

  def fun(f: (Int, Int) => Int): (String) => Unit = {

    val i = f(100, 200)

    (s: String) => {

      println(s + i)

    }

  }



  val result = fun((a: Int, b: Int) => {

    a + b

  })

  result("100+200=")

  //也可以简写成

  fun((a,b)=>{a+b})("100+200=")

柯里化函数

柯里化函数其实在高阶函数中我们已经见过他的形式

比如上边例子的最后一行:fun((a,b)=>{a+b})("100+200=")

 

  def fun(a:Int,b:Int)(c:Int,d:Int)={

    a+b+c+d

  }

  fun(1,2)(3,4)

回顾上一节

学习下一节

猜你喜欢

转载自blog.csdn.net/dcc15011003101/article/details/105983794