有没有更好的方法在kotlin中编写CompletableFutrue.XXXasync()调用?

时间:2017-06-24 08:47:30

标签: kotlin completable-future

Java CompletableFuture<T>有很多异步方法,静态或实例,格式为

public <U> CompletableFuture<U> XXXasync(SomeFunctionalInterface<T> something, Executor executor)

如果您对kotlin中的FP有足够的经验,您会立即意识到这些功能在kotlin中使用非常笨拙,因为SAM接口不是最后一个参数。

aCompletableFutrue.thenComposeAsync(Function<SomeType, CompletableFuture<SomeOtherType>> { 
                               //   ^ WHAT A LONG TYPE NAME THAT NEED TO BE HAND WRITTEN
    // do something that has to be written in multiple lines.
    // for that sake of simplicity I use convert() to represent this process
    convert(it)
}, executor)

Function有一个非常长的通用签名,我不知道如何让IDE生成。如果类型名称变得更长或包含ParameterizedType或具有类型方差注释,那么它将是一个简单的对接。

由于第5行尾随, executor),它看起来也很讨厌。

kotlin或IDE中是否有一些缺少功能可以帮助解决这种情况?至少我不想自己编写那个长SAM构造函数。

拒绝解决方案:

  1. 使用命名参数似乎不起作用,因为此功能仅适用于kotlin函数。

  2. 放弃异步方法从一开始听起来很糟糕。

  3. Kotlin corountine被拒绝,因为我们正在使用一些仅接受CompletionStage的愚蠢Java库。

1 个答案:

答案 0 :(得分:3)

IF 你从java中调用api,最后获取了一个函数接口参数,你可以在kotlin中使用lambda。

val composed: CompletableFuture<String> = aCompletableFutrue.thenComposeAsync { 
    CompletableFuture.supplyAsync { it.toString() }
};

其次,如果您不喜欢java api方法签名。您可以编写自己的扩展方法,例如:

fun <T, U> CompletableFuture<T>.thenComposeAsync(executor: Executor
      , mapping: Function1<in T, out CompletionStage<U>>): CompletableFuture<U> {
    return thenComposeAsync(Function<T,CompletionStage<U>>{mapping(it)}, executor)
}

那么你可以沿着方法制作lambda。

aCompletableFutrue.thenComposeAsync(executor){
  // do working
}