写kotlin越来越久,很多代码尽管能看懂,而且能去改,可是不知道他用了啥,里边的原理是什么,举个例子?大家一起学习一下吧
内联函数
顾名思义,可是在项目中我遇到得很少,他比较适用于一些包装方法的写法,比如下面这个
inline fun measureTimeMillis(block: () -> Unit): Long {
val startTime = System.currentTimeMillis()
block()
return System.currentTimeMillis() - startTime
}
val time = measureTimeMillis {
// code to be measured here
}
println("Time taken: $time ms")
这样的函数,今后如果想要测一段代码的运转时间,只需要将measureTimeMillis包着他就行
类型别号
一个很奇特的东西,允许为现有类型界说新称号
data class Person(val name: String, val age: Int)
typealias People = List<Person>
val people: People = listOf(
Person("Alice", 25),
Person("Bob", 30),
Person("Charlie", 35)
)
fun findOlderThan(people: People, age: Int): People {
return people.filter { it.age > age }
}
fun main() {
val olderPeople = findOlderThan(people, 30)
println(olderPeople)
}
其间People便是一个别号,如果使用typealias代替直接界说list,项目中就会少很多后缀为list的列表,少了类似于personlist这种变量,在查找,大局替换,修改时也会愈加直观看到person和people的区别场景
typealias能够被大量使用在list, map乃至于函数中,因为这些命名或许会比较长,替换后能够提高可读性
高阶函数
一个一开始很难了解,了解后又真香的函数,我愿称了解的那一刻为程序员进阶闪烁时,当一个老程序员回首往事时,他不会因为虚度年华而悔恨,可是一定会因为不懂高阶函数而羞耻
尤其是在项目中发现这种函数,又看不懂时,是万万不敢问同事的,所以,请现在就了解清楚吧
fun calculate(x: Int, y: Int, operation: (Int, Int) -> Int): Int {
return operation(x, y)
}
fun main() {
val sum = calculate(10, 5) { x, y -> x + y }
println("Sum is $sum")
val difference = calculate(10, 5) { x, y -> x - y }
println("Difference is $difference")
}
能够看到,calculate其实并没有做什么,只是履行了传入进来的operation,这,便是高阶函数,所谓领导也是如此,优秀的部属,往往将计划随着问题传入进来,领导只需指示一下履行operation即可
配合上lambda准则,最终一个参数能够提出到括号外面,也便是讲operation提出到外面的{}中,交给调用方自己履行,就形成了这样的写法
val sum = calculate(10, 5) { x, y -> x + y }
了解这一点后,一下子就清晰了很多,calculate看起来什么都没做,他却成为了世界上功用最强大,最灵敏,bug最少的核算两个数运算成果的函数
深化
了解上面分析,现已满足咱们在kotlin项目中进阶了,现在,咱们来看下高阶函数反编译后的java代码
public final class TestKt {
public static final int calculate(int x, int y, @NotNull Function2 operation) {
Intrinsics.checkNotNullParameter(operation, "operation");
return ((Number)operation.invoke(x, y)).intValue();
}
public static final void main() {
int sum = calculate(10, 5, (Function2)null.INSTANCE);
String var1 = "Sum is " + sum;
System.out.println(var1);
int difference = calculate(10, 5, (Function2)null.INSTANCE);
String var2 = "Difference is " + difference;
System.out.println(var2);
}
// $FF: synthetic method
public static void main(String[] var0) {
main();
}
}
尽管java的完成太不优雅,可是咱们能够看出,高阶函数,本质上传入的函数是一个名为Function2的目标,
public interface Function2<in P1, in P2, out R> : Function<R> {
/** Invokes the function with the specified arguments. */
public operator fun invoke(p1: P1, p2: P2): R
}
他是kotlin包自带的函数,看起来能够用来在反编译中替换匿名lambda表达式,将其逻辑移动到本身的invoke中,然后生成一个Function2目标,这样完成kotlin反编译为java时的lambda替换
这也是高阶函数得以完成的根本原因