【问题标题】:How does the following codes of Lambda Expression execute?Lambda 表达式的以下代码是如何执行的?
【发布时间】:2021-05-02 14:28:57
【问题描述】:

我创建了一个 customFilter 来理解 Kotlin 中的 Lambda 表达式。代码如下;

我已经了解我们如何创建自己的自定义过滤器函数,如何在高阶函数中传递 lambda,但无法弄清楚这些行的执行顺序。

    //Create a class extension function on List<Shape> called customFilter which takes a lambda function as argument
    //and returns a Boolean value. The class extension function returns a List
    fun List<Shape>.customFilter(filterFunction: (Shape, String) -> (Boolean)): List<Shape> {
        val resultList = mutableListOf<Shape>()
        for (shape in this) {
            if (filterFunction(shape)) {
                
                resultList.add(shape)
            }
        }
    
        return resultList
    }
     fun main(){
//assume all the following instances has been created.
     var shapes2 = listOf(circle1, circle2, triangle1, triangle2, rectangle1, rectangle2)
    
        shapes2 = shapes2.customFilter { shape, stringVar ->
            println(stringVar)
            shape.area() > 20
        }.sortedBy { item -> item.area() }
     
    }

下面的代码中会根据哪个条件计算sum?

fun main() {
    val list = (1..5).toList()

    val sum = list.customSum { item -> item % 2 == 0 }

    println(sum)
}

fun List<Int>.customSum(sumFunction: (Int) -> Boolean): Int {

    var sum = 0

    for (number in this) {
        if (number % 2 == 1)
            sum += number
    }
    return sum

} 

【问题讨论】:

  • 为什么不添加打印语句/使用调试器自己找出来?
  • 我已经添加了,找不到输出模式背后的任何概念。
  • 您更新的问题有一个问题 - 您从未真正执行过您传递给 customSum 的 lambda。你应该做的是:for (number in this) { if (someFunction(number)) { sum += number } } 然后返回总和。
  • 也许这样说会有所帮助 - 函数是 Kotlin 中的一流原语。意思是,它是一个东西,你可以传递,然后使用 - 即使你还不知道 lambda 的定义。关键是它们是基于签名(例如(Int) -&gt; Boolean)进行类型化的(如在类型中),因此 Kotlin 可以在 Java 中生成适当的泛型/类。

标签: kotlin lambda functional-programming anonymous-function


【解决方案1】:

您的 lambda 被传递给您的 customFilter 函数,然后执行。

操作顺序,如果你要从图片中去掉 lambda-passing,可能是这样的:

fun customFilteredList(shapes: List<Shape>): List<Shape> {
    val resultList = mutableListOf<Shape>()
    for (shape in shapes) {
        if (shape.area() > 20) {
            resultList.add(shape)
        }
    }
    return resultList
}

fun main() {
    // same instances from before
    val shapesBefore = listOf(circle1, circle2, triangle1, triangle2, rectangle1, rectangle2)
    val shapesAfter = customFilteredList(shapesBefore)
    // do more stuff
}

我希望区别很明显。通过定义任何接受 lambda(而不仅仅是一个过滤器)的函数,您正在将对该整个 lambda(其本身的范围)的引用传递给您的函数。届时,您的函数将在其自己的范围内执行 lambda。所有这些都在您的main() 调用范围内执行。

顺便说一句(它对我有用)是 filter 是在 kotlin 标准库中实现的 lambda 接受函数。

fun main() {
    val shapes = listOf(circle1, circle2, triangle1, triangle2, rectangle1, rectangle2).filter { shape ->
        shape.area() > 20
    }
}

我不确定您的 stringVar 来自哪里,所以我不确定您在打印它之外的功能中会发生什么。如果没有更多上下文来说明为什么在更新列表时需要该字符串,这真的没有意义。

【讨论】:

  • 谢谢。这很有帮助。 stringVar 我添加了一些打印语句来了解语句执行的时间顺序。
  • 解说真的很酷,谢谢。
  • 嘿@tsalaroth,在下面的代码中,根据哪个条件计算总和?我用以下代码编辑了主要问题。 fun main() { val list = (1..5).toList() val sum = list.customSum { item -> item % 2 == 0 } println(sum) } fun List.customSum(sumFunction: (Int) -> Boolean): Int { var sum = 0 for (number in this) { if (number % 2 == 1) sum += number } return sum }
猜你喜欢
  • 2020-02-01
  • 2021-12-02
  • 2011-08-10
  • 2023-03-03
  • 1970-01-01
  • 1970-01-01
  • 2019-12-30
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多