You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用Lambda简化Kotlin中FooClass的foo函数调用?

没问题,我来帮你理清楚怎么用Lambda简化这个调用!

首先得说明一个关键点:Kotlin的SAM(Single Abstract Method)转换只支持单个抽象方法的接口,而你的Listener<T>有两个抽象方法(onSuccess和onFailure),所以没法直接用一个Lambda代替整个匿名内部类。不过我们有两种简单的方式来实现你想要的简化调用效果:

方式一:给foo函数添加高阶函数重载

这是最直接的方案,不需要修改原有的Listener接口,只需要在FooClass里新增一个重载的foo函数,把Listener拆成两个独立的Lambda参数:

// 在FooClass中新增这个重载函数
fun foo(id: Int, onSuccess: (JsonElement?) -> Unit, onFailure: () -> Unit) {
    // 内部还是调用原有的foo方法,用匿名内部类适配Listener
    enqueue(object : Listener<JsonElement> {
        override fun onSuccess(result: JsonElement?) = onSuccess(result)
        override fun onFailure() = onFailure()
    }, apiService.getFoo(id))
}

现在调用的时候就可以用简洁的Lambda写法了,还能利用Kotlin的命名参数和尾随Lambda特性:

// 写法1:用命名参数,逻辑清晰
FooClass().foo(id,
    onSuccess = { result ->
        // 这里写onSuccess的处理逻辑
        println("成功拿到结果:$result")
    },
    onFailure = {
        // 这里写onFailure的处理逻辑
        println("请求失败了")
    }
)

// 写法2:把最后一个Lambda放在括号外(尾随Lambda),更简洁
FooClass().foo(id, { result ->
    println("成功拿到结果:$result")
}) {
    println("请求失败了")
}

方式二:用密封类+单个Lambda处理两种结果

如果你更倾向于用单个Lambda来统一处理成功和失败的逻辑,可以先定义一个密封类来封装请求结果,再给foo添加对应的重载:

第一步,定义密封类:

sealed class RequestResult<out T> {
    data class Success<out T>(val data: T?) : RequestResult<T>()
    object Failure : RequestResult<Nothing>()
}

第二步,新增foo的重载函数:

fun foo(id: Int, handler: (RequestResult<JsonElement>) -> Unit) {
    enqueue(object : Listener<JsonElement> {
        override fun onSuccess(result: JsonElement?) {
            handler(RequestResult.Success(result))
        }
        override fun onFailure() {
            handler(RequestResult.Failure)
        }
    }, apiService.getFoo(id))
}

现在调用的时候就可以用单个Lambda,配合when表达式处理两种情况,和你想要的写法非常接近:

FooClass().foo(id) { result ->
    when (result) {
        is RequestResult.Success -> {
            // 处理成功逻辑,result.data就是返回的JsonElement?
            println("成功:${result.data}")
        }
        RequestResult.Failure -> {
            // 处理失败逻辑
            println("请求失败")
        }
    }
}

补充说明

如果你的Listener是Java接口,Kotlin虽然支持自动SAM转换,但因为它有两个抽象方法,依然没法用单个Lambda代替,所以上面的两种方案同样适用。

内容的提问来源于stack exchange,提问作者Gabi Moreno

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.29 07:54:54