Kotlin中的部分功能应用

时间:2017-11-08 13:43:13

标签: kotlin partial-application

我遇到部分功能应用的语法问题。以下代码工作正常,并输出:two-three-four

import kotlin.coroutines.experimental.*

inline fun <T> Iterable<T>.forEachFrom(beg:Int, act:(T)->Unit) {
  var i=0;  if (beg>=0) for (e in this) if (i++ >= beg) act(e)
}    // sample function I am testing; please don't change this!

fun main(a:Array<String>) {
  val l = listOf("zero", "one", "two", "three", "four")
  fun test() = buildSequence { l.forEachFrom(2) { yield(it) } }.joinToString("-")
  println(test())
}

我想封装我的test(),因此它被称为: test(l.forEachFrom(2))但是,我似乎无法使类型/语法正确。  如何重新编写test()函数定义以实现此目的?

1 个答案:

答案 0 :(得分:0)

目前尚不清楚您要实现的目标。如果您提供更多详细信息,我们可以提供更好的答案。也就是说,以下代码有望为您指明正确的方向。

import kotlin.coroutines.experimental.*

inline fun <T,S> Iterable<T>.mapFrom(beg:Int, act:(T)->S) =
    drop(beg).map {act(it)}

fun main(a:Array<String>) {
    val l = listOf("zero", "one", "two", "three", "four")
    fun <T> test(values: List<T>) = values.joinToString("-")
    println(test(l.mapFrom(2) {it}))
}

forEachFrom并不是真正被用作forEach,而是被用作map。这是主要问题,因为您正在使用yield输出结果,而不仅仅是返回结果。如果forEachFrom也要用于其副作用,则仍可以将其用于该目的。

此外,test没有理由将一个函数作为参数,而不仅仅是接受该函数的输出作为其参数。 buildSequence调用也是多余的,因为您立即调用joinToString,这是终端操作,并迫使在buildSequence内部进行急切的函数计算。