RxKotlin使用方法引用collectInto()MutableList
以下代码是我尝试将RxJava示例转换为Kotlin。 它应该收集一串Int
到MutableList
,但是我得到了大量的错误。
val all: Single<MutableList<Int>> = Observable .range(10, 20) .collectInto(::MutableList, MutableList::add)
错误:
Error:(113, 36) Kotlin: Type inference failed: Not enough information to infer parameter T in inline fun <T> MutableList(size: Int, init: (index: Int) -> T): MutableList<T> Please specify it explicitly. Error:(113, 49) Kotlin: One type argument expected for interface MutableList<E> : List<E>, MutableCollection<E> defined in kotlin.collections Error:(113, 67) Kotlin: None of the following functions can be called with the arguments supplied: public abstract fun add(element: Int): Boolean defined in kotlin.collections.MutableList public abstract fun add(index: Int, element: Int): Unit defined in kotlin.collections.MutableList
如果我更改ImmutableList::add
到ImmutableList<Int>::add
,我摆脱了类型参数期望的错误,它被替换为:
Error:(113, 22) Kotlin: Type inference failed: fun <U : Any!> collectInto(initialValue: U!, collector: ((U!, Int!) -> Unit)!): Single<U!>! cannot be applied to (<unknown>,<unknown>)
这是Java中以下内容的直接副本:
Observable<List<Integer>> all = Observable .range(10, 20) .collect(ArrayList::new, List::add);
我明白,第一个错误是告诉我这是要推断不正确的类型,我需要更明确(哪里?),但我认为::MutableList
将等同于() -> MutableList<Int>
。 第三个错误是告诉我,它不能用参数调用任何add()
方法,但是我认为MutableList::add
等价于{ list, value -> list.add(value) }
。 第四个错误告诉我,它不能找出应用到collector
的类型。
如果我使用lambda表达式来代替,则不会有错误:
val all: Single<MutableList<Int>> = Observable .range(10, 20) .collectInto(mutableListOf(), { list, value -> list.add(value) }) all.subscribe { x -> println(x) }
我会很感激一些关于我在做什么错误的方法引用的评论,因为显然有一些我误解了(通过Kotlin语言参考 ,我想知道这是否是一个语言功能呢?)。 非常感激。
在第一个示例中,您尝试将collect
的方法签名应用于collectInto
的方法签名。
这是行不通的,因为collect
需要一个Func0<R>
和一个Func0<R>
Action2<R, ? super T>
和collectInto
期望一个真实的对象和一个BiConsumer<U, T>
。
构造函数的引用不能为collectInto
工作 – 你需要一个真正的对象(例如你的mutableListOf()
调用)
第二个问题是Kotlin期待BiConsumer
对象而不是函数。 我不太清楚为什么。 显然,Kotlin无法处理来自SAM-Interfaces的lambdas和函数引用的多个泛型。
因此,您需要传递一个BiConsumer
的实例,而不仅仅是一个函数。
这也是为什么我在评论中问你是否确定错误信息:
range(10, 20).collectInto(mutableListOf(), { l, i -> l.add(i) })
会给我一个错误,而
range(10, 20).collectInto(mutableListOf(), BiConsumer { l, i -> l.add(i) })
惯于。