美文网首页
Kotlin-函数和lambda表达式学习笔记

Kotlin-函数和lambda表达式学习笔记

作者: 郑在学_blog | 来源:发表于2017-07-22 11:28 被阅读0次

1.Kotlin函数可以使用中缀表示法来调用,当满足一下条件时:

infix fun Int.add(x:Int):Int{
    return this+x
}

fun printAdd(){
    val value=2 add 3//中缀表示法调用add函数(不用加".")
    print("the value is $value")
}

2.在Kotlin中,调用函数的时候可以使用命名的参数:

fun foo(arg1:String="Hello Kotlin",arg2:Boolean,arg3:Int){
    print("arg1="+arg1+"&arg2="+arg2+"arg3="+arg3)
}

fun printFoo(){
    foo(arg2 = true,arg3 = 7)//命名参数调用foo函数
}

3.Kotlin函数定义可变数量的参数,只要用vararg关键字修饰即可:

//可变数量的参数
fun foo4(vararg args:Int){
    for (arg in args){
        print(arg.toString()+",")
    }
}

fun printFoo4(){
    foo4(1,2,3,4,5)//1,2,3,4,5,
}

4.Kotlin函数以数组的内容作为参数,只要用伸展(spread)操作符(在数组前面加 *):

fun foo4(vararg args:Int){
    for (arg in args){
        print(arg.toString()+",")
    }
}

fun printFoo4(){
    val values= intArrayOf(1,2,3,4,5)
    foo4(*values)//使用扩展运算符传一个数组给可变参数
}

5.高阶函数

高阶函数可以将一个函数作为参数或返回值:

fun add2(x:Int=0,y:Int=0):Int{
    return x+y
}

fun operate(x:Int=0,y:Int=0,body:(Int,Int)->Int){//body是一个函数类型,传入两个Int类型参数,返回一个Int类型参数
    print("this result is "+body(x,y))
}

fun getValue(){
    operate(3,7,::add2)
}

6.Lambda表达式

Lambda表达式通常使用“{ }”包围,参数是定义在“()”内,实体部分跟在“->”后面;
以上的operate()方法,我们还有一个更简洁的调用方式,即传入一个lambda表达式:

operate(3,7,{x,y->x+y})//函数参数传入一个lambda表达式

当函数参数是最后函数的最后一个参数,并且你传入一个lambda表达式作为相应的参数,则可以在圆括号之外指定它:

operate(3,7){//函数参数作为函数的最后一个参数,并且传入的是一个lambda表达式,可以在在圆括号外指定
        x,y->x+y

如果lambda表达式只有一个参数,kotlin可以自己计算出签名,它允许我们不声明唯一的参数,并且隐含的为我们声明其名称为it:

fun upCase(str:String,body:(String)->String):String{//body是一个函数参数,传入一个String类型参数,返回一个String类型
    return body(str)
}
fun transform(){
    upCase("HelloKotlin"){//函数字面值只有一个参数,可以省略参数声明,其名称是it
        it.toUpperCase()
    }
}

如果lambda表达式是调用的唯一参数,则调用中的圆括号可以完全省略。

7.匿名函数

匿名函数与常规函数一样,只是省略了函数名称:

fun String.upper(body:(String)->String):String{
    return body(this)
}

fun transform(){
    "HelloKotlin".upper { it.toUpperCase() }//lambda表达式是调用的唯一参数,则调用的圆括号可以省略
    "HelloKotlin".upper(fun(str:String):String{//将匿名函数作为一个函数参数传入
        return str.toUpperCase()
    })
}

匿名函数 与 Lambda表示式区别:

  • 匿名函数作为参数,一般定义在“()”中;而Lambda表达式可以定义到调用函数“()”外。
  • 另外区别在“非局部返回(non-local returns)”行为上:非标签注解的return(返回对应的最内层的函数(即fun)),在匿名函数中,退出该匿名函数;而在Lambda表达中,退出包含该表达式的函数。
fun foo() {
    ints.forEach {
        if (it == 0) return//这个 return 表达式从最直接包围它的函数即 foo 中返回。
        print(it)
    }
}
fun transform():String{
    "HelloKotlin".upper {
        print(it.toUpperCase())
        return@upper it.toUpperCase()//返回必须加标签限制
    }
    "HelloKotlin".upper(fun(str:String):String{
        return str.toUpperCase()//从匿名函数返回
    })
}

8.内嵌函数

作为自变量接收的函数令人讨厌的是编译器需要为它们创建类,这将影响性能。但是,这可以用保留字inline容易地解决。

由于Inline函数是在编译时将它的代码替换对它的调用,所以在性能方面影响较少。为此,它不需要用额为的对象。

我们能够转换doAsync到一个inline函数:

inline fun doAsync(crossinline f: () -> Unit) {
    Thread({ f() }).start()
}

在这个例子中,由于我们从另一个执行内容(另一个Lambda表达式)中调用f(),所以要求crossinline。不用太担心这些,在需要使用它时,编译器会提醒你的。

现在,在我们的代码中,产生异步代码块:

doAsync { 
    op1()
    op2()
    op3()
}

这样在{}内的每件事都将在第二个线程中执行。

参考文章

相关文章

网友评论

      本文标题:Kotlin-函数和lambda表达式学习笔记

      本文链接:https://www.haomeiwen.com/subject/fzfykxtx.html