Kotlin函数式编程

目录

函数式编程的特点

声明函数

Lambda表达式

高阶函数

案例


函数式编程的特点

函数式编程本质是函数的集合,比如想要过滤一个集合中的奇数:

fun testFunX(): Unit {
    val list = listOf(1,2,3,4,5,6,7)
    val lx = list.filter { it %2 == 1 } // filter函数,参数是lambda表达式
    println(list)
    println(lx)
}

函数式编程是关于不变性的编程范式;
函数式编程是关于函数集合的编程范式;

函数式编程的特点:

  • 函数也是一种数据类型,可以作为参数,同时函数的返回值也可以是函数 —— 函数既可以作参数,也可以作返回值,即一等函数支持
  • 纯函数,不改变外部的数据结构,是没有副作用的函数。不去修改数据,会创建一份新的数据映射,会使用不可变的数据。
  • 函数的组合(compose function):
    • 函数式编程通过不同函数的组合来构建程序的逻辑。
    • 面向对象编程是通过对象之间发送消息来构建程序的逻辑。

声明函数

  • 声明函数
// 使用 fun 关键字来声明函数
fun sum1(x: Int, y: Int): Int {
    return x + y
}
  • 声明函数类型的变量
    函数也可以当作变量来使用,声明一个函数类型的变量 sum2 :
val sum2 = fun (x: Int, y: Int):Int {return x + y}

fun testSum2(): Unit {
    println(sum2)   // 输出: (kotlin.Int, kotlin.Int) -> kotlin.Int
    println(sum2(3,9))   // 输出: 12
}

(kotlin.Int, kotlin.Int) -> kotlin.Int —— 这个带“->”的表达式就是一个函数类型
表示一个 输入两个Int类型值、输出一个Int类型值 的函数。 

 

  • 其它形式 声明函数
// 使用表达式声明sumX()函数
fun sumX(x: Int, y: Int) = x+y

// 使用fun关键字声明了一个匿名函数,同时直接使用表达式来实现函数
// { x+y } 的类型是 () -> kotlin.Int 函数;{ x+y }表达式返回的是一个Lambda表达式
val sumF = fun(x: Int, y: Int) = { x+y }

// 使用表达式声明 sumF2()函数,{}表示一个Lambda表达式
fun sumF2(x: Int, y: Int) = { x + y }

 

Lambda表达式

fun testFunX(): Unit {
    val list = listOf(1,2,3,4,5,6,7)
    val lx = list.filter { it %2 == 1 } // filter()函数,参数是lambda表达式
    println(list)
    println(lx)
}

filter()函数的参数 { it %2 == 1 } 是lambda表达式,
filter()函数的参数只有一个,因此括号省略了。

filter()函数的完整写法:

list.filter({ it %2 == 1 })
// 或
list.filter({ it -> it %2 == 1 })

 

filter()函数的声明:

public inline fun <T> Iterable<T>.filter(predicate: (T) -> Boolean): List<T> {
    return filterTo(ArrayList<T>(), predicate)
}

public inline fun <T, C : MutableCollection<in T>> Iterable<T>.filterTo(destination: C, predicate: (T) -> Boolean): C {
    for (element in this) if (predicate(element)) destination.add(element)
    return destination
}

filter()函数的参数是 一个函数 predicate: (T) -> Boolean .

testFunX()函数完整写法:

val isOdd = {it: Int -> it %2 ==1} // lambda表达式

fun testFunY(): Unit {
    val list = listOf(1,2,3,4,5,6,7)
    val lx = list.filter(isOdd)	// lambda表达式作为参数
    println(list)
    println(lx)		// 输出:[1, 3, 5, 7]
    println(isOdd)	// 输出:(kotlin.Int) -> kotlin.Boolean
}

 

高阶函数

Kotlin高阶函数:以另一个函数为参数或者返回值的函数。
高阶函数是多个函数的复合。

知识点:类型别名 typealias

案例:输入一个字符串列表,过滤出字符串元素长度为奇数的列表并输出。

1 . 可以将这个需求拆解成两个函数来解决:

val len = fun (s: String?) = s?.length ?:0  // 计算字符串的长度
val odd = fun (i:Int) = i%2 == 1    // 判断输入值是否是奇数

2 . 再使用函数 so 来封装"字符串的长度是否是奇数"的逻辑

// 封装"字符串的长度是否是奇数"
val so = fun (len: (String?)->Int, odd:(Int)->Boolean) : (String?)->Boolean = {odd(len(it))}

 3 . 这个函数的声明比较长,可以简化一下:

// 使用类型别名来简化函数类型:
typealias L = (String?)->Int
typealias O = (Int)->Boolean
typealias S = (String?)->Boolean

3 .1. 简化后的so函数

// 简化 so 函数的写法:
val sop = fun (len: L, odd: O) : S = {odd(len(it))}

// {odd(len(it))} 是 lambda表达式,返回的是一个 (String?)->Boolean函数类型

4 . 测试

fun testSLO(): Unit {
	val strList = listOf("x","xy","xyz","xyz1","xyz12","xyz123","xyz1234")
    println(strList)
    println(strList.filter(so(len,odd)))  // 输出:[x, xyz, xyz12, xyz1234]
    println(strList.filter(sop(len,odd))) // 输出:[x, xyz, xyz12, xyz1234]
    println(strList)
}

so(len,odd) 以及 sop(len,odd) 这样的复合函数代码 和 数学公式很接近,简单易懂。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值