#KT-39 Fixed with eager and lazy implementations
This commit is contained in:
@@ -1,7 +1,7 @@
|
||||
package kotlin
|
||||
|
||||
import kotlin.support.AbstractIterator
|
||||
import kotlin.support.FunctionIterator
|
||||
import kotlin.support.*
|
||||
import java.util.Collections
|
||||
|
||||
/**
|
||||
* Returns an iterator which invokes the function to calculate the next value on each iteration until the function returns *null*
|
||||
@@ -110,6 +110,32 @@ private class FlatMapIterator<T, R>(val iterator : java.util.Iterator<T>, val tr
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates an [[Iterator]] which iterates over this iterator then the given element at the end
|
||||
*
|
||||
* @includeFunctionBody ../../test/iterators/IteratorsTest.kt plus
|
||||
*/
|
||||
public inline fun <in T> java.util.Iterator<T>.plus(element: T): java.util.Iterator<T> {
|
||||
return CompositeIterator<T>(this, SingleIterator(element))
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Creates an [[Iterator]] which iterates over this iterator then the following iterator
|
||||
*
|
||||
* @includeFunctionBody ../../test/iterators/IteratorsTest.kt plusCollection
|
||||
*/
|
||||
public inline fun <in T> java.util.Iterator<T>.plus(iterator: java.util.Iterator<T>): java.util.Iterator<T> {
|
||||
return CompositeIterator<T>(this, iterator)
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates an [[Iterator]] which iterates over this iterator then the following collection
|
||||
*
|
||||
* @includeFunctionBody ../../test/iterators/IteratorsTest.kt plusCollection
|
||||
*/
|
||||
public inline fun <in T> java.util.Iterator<T>.plus(collection: java.lang.Iterable<T>): java.util.Iterator<T> = plus(collection.iterator())
|
||||
|
||||
/**
|
||||
* Returns an iterator containing all the non-*null* elements, lazily throwing an [[IllegalArgumentException]]
|
||||
if there are any null elements
|
||||
|
||||
@@ -39,6 +39,29 @@ public inline fun <T> java.lang.Iterable<T?>?.filterNotNull() : List<T> = filter
|
||||
*/
|
||||
public inline fun <T, R> java.lang.Iterable<T>.flatMap(transform: (T)-> Collection<R>) : Collection<R> = flatMapTo(ArrayList<R>(), transform)
|
||||
|
||||
/**
|
||||
* Creates a copy of this collection as a [[List]] with the element added at the end
|
||||
*
|
||||
* @includeFunctionBody ../../test/CollectionTest.kt plus
|
||||
*/
|
||||
public inline fun <in T> java.lang.Iterable<T>.plus(element: T): List<in T> {
|
||||
val list = to(ArrayList<T>())
|
||||
list.add(element)
|
||||
return list
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Creates a copy of this collection as a [[List]] with all the elements added at the end
|
||||
*
|
||||
* @includeFunctionBody ../../test/CollectionTest.kt plusCollection
|
||||
*/
|
||||
public inline fun <in T> java.lang.Iterable<T>.plus(elements: java.lang.Iterable<T>): List<T> {
|
||||
val list = to(ArrayList<T>())
|
||||
list.addAll(elements.toCollection())
|
||||
return list
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a list containing all the non-*null* elements, throwing an [[IllegalArgumentException]] if there are any null elements
|
||||
*
|
||||
|
||||
@@ -53,45 +53,6 @@ public inline fun <in T: java.lang.Comparable<T>> java.lang.Iterable<T>.toSorted
|
||||
public inline fun <in T: java.lang.Comparable<T>> java.lang.Iterable<T>.toSortedList(comparator: java.util.Comparator<T>) : List<T> = toList().sort(comparator)
|
||||
|
||||
|
||||
/**
|
||||
* Creates a new [[List]] with the element added at the end
|
||||
*
|
||||
* @includeFunctionBody ../../test/CollectionTest.kt plus
|
||||
*/
|
||||
public inline fun <in T> java.util.Collection<T>.plus(element: T): List<in T> {
|
||||
val list = to(ArrayList<T>())
|
||||
list.add(element)
|
||||
return list
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds the element to this collection
|
||||
*
|
||||
* @includeFunctionBody ../../test/CollectionTest.kt plusAssign
|
||||
*/
|
||||
public inline fun <in T, C: java.util.Collection<in T>> C.plusAssign(element: T): C {
|
||||
add(element)
|
||||
return this
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a new [[List]] with the element added at the end
|
||||
*/
|
||||
/*
|
||||
public inline fun <in T> java.util.Collection<T>.plus(elements: java.lang.Iterable<T>): List<T> = toList().plusAssign(elements)
|
||||
*/
|
||||
|
||||
/**
|
||||
* Adds all the elements to this collection
|
||||
*/
|
||||
/*
|
||||
public inline fun <in T, C: Collection<in T>> C.plusAssign(elements: java.lang.Iterable<T>): C {
|
||||
addAll(elements.toCollection())
|
||||
return this
|
||||
}
|
||||
*/
|
||||
|
||||
|
||||
// List APIs
|
||||
|
||||
public inline fun <in T: java.lang.Comparable<T>> List<T>.sort() : List<T> {
|
||||
|
||||
@@ -32,7 +32,9 @@ public abstract class AbstractIterator<T>: java.util.Iterator<T> {
|
||||
return next.sure()
|
||||
}
|
||||
|
||||
override fun remove() { throw UnsupportedOperationException() }
|
||||
override fun remove() {
|
||||
throw UnsupportedOperationException()
|
||||
}
|
||||
|
||||
/** Returns the next element in the iteration without advancing the iteration */
|
||||
fun peek(): T {
|
||||
@@ -75,7 +77,7 @@ public abstract class AbstractIterator<T>: java.util.Iterator<T> {
|
||||
}
|
||||
|
||||
/** An [[Iterator]] which invokes a function to calculate the next value in the iteration until the function returns *null* */
|
||||
class FunctionIterator<T>(val nextFunction : () -> T?) : AbstractIterator<T>() {
|
||||
class FunctionIterator<T>(val nextFunction: () -> T?): AbstractIterator<T>() {
|
||||
|
||||
override protected fun computeNext(): Unit {
|
||||
val next = (nextFunction)()
|
||||
@@ -86,3 +88,47 @@ class FunctionIterator<T>(val nextFunction : () -> T?) : AbstractIterator<T>() {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/** An [[Iterator]] which iterates over a number of iterators in sequence */
|
||||
class CompositeIterator<T>(vararg iterators: java.util.Iterator<T>): AbstractIterator<T>() {
|
||||
|
||||
val iteratorsIter = iterators.iterator()
|
||||
var currentIter: java.util.Iterator<T>? = null
|
||||
|
||||
override protected fun computeNext(): Unit {
|
||||
while (true) {
|
||||
if (currentIter == null) {
|
||||
if (iteratorsIter.hasNext) {
|
||||
currentIter = iteratorsIter.next()
|
||||
} else {
|
||||
done()
|
||||
return
|
||||
}
|
||||
}
|
||||
val iter = currentIter
|
||||
if (iter != null) {
|
||||
if (iter.hasNext()) {
|
||||
setNext(iter.next())
|
||||
return
|
||||
} else {
|
||||
currentIter = null
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/** A singleton [[Iterator]] which invokes once over a value */
|
||||
class SingleIterator<T>(val value: T): AbstractIterator<T>() {
|
||||
var first = true
|
||||
|
||||
override protected fun computeNext(): Unit {
|
||||
if (first) {
|
||||
first = false
|
||||
setNext(value)
|
||||
} else {
|
||||
done()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -258,17 +258,30 @@ class CollectionTest {
|
||||
val list2 = list + "cheese"
|
||||
assertEquals(arrayList("foo", "bar"), list)
|
||||
assertEquals(arrayList("foo", "bar", "cheese"), list2)
|
||||
|
||||
// lets use a mutable variable
|
||||
var list3 = arrayList("a", "b")
|
||||
list3 += "c"
|
||||
assertEquals(arrayList("a", "b", "c"), list3)
|
||||
}
|
||||
|
||||
test fun plusAssign() {
|
||||
var list = arrayList("foo", "bar")
|
||||
/*
|
||||
TODO should we have plus and plus assign work differently for collections?
|
||||
see KT-1710
|
||||
/*
|
||||
TODO compiler fails on this one
|
||||
|
||||
list += "cheese"
|
||||
assertEquals(arrayList("foo", "bar", "cheese"), list)
|
||||
*/
|
||||
val list = arrayList("foo", "bar") + arrayList("cheese", "wine")
|
||||
*/
|
||||
test fun plusCollection() {
|
||||
val a = arrayList("foo", "bar")
|
||||
val b = arrayList("cheese", "wine")
|
||||
val list = a + b
|
||||
assertEquals(arrayList("foo", "bar", "cheese", "wine"), list)
|
||||
|
||||
// lets use a mutable variable
|
||||
var ml = a
|
||||
ml += "beer"
|
||||
ml += b
|
||||
ml += "z"
|
||||
assertEquals(arrayList("foo", "bar", "beer", "cheese", "wine", "z"), ml)
|
||||
}
|
||||
|
||||
test fun requireNoNulls() {
|
||||
|
||||
@@ -52,6 +52,32 @@ class IteratorsTest {
|
||||
assertEquals("13, 21, 34, 55, 89, ...", fibonacci().filter { it > 10 }.makeString(separator = ", ", limit = 5))
|
||||
}
|
||||
|
||||
test fun plus() {
|
||||
val iter = arrayList("foo", "bar").iterator()
|
||||
val iter2 = iter + "cheese"
|
||||
assertEquals(arrayList("foo", "bar", "cheese"), iter2.toList())
|
||||
|
||||
// lets use a mutable variable
|
||||
var mi = arrayList("a", "b").iterator()
|
||||
mi += "c"
|
||||
assertEquals(arrayList("a", "b", "c"), mi.toList())
|
||||
}
|
||||
|
||||
test fun plusCollection() {
|
||||
val a = arrayList("foo", "bar")
|
||||
val b = arrayList("cheese", "wine")
|
||||
val iter = a.iterator() + b.iterator()
|
||||
assertEquals(arrayList("foo", "bar", "cheese", "wine"), iter.toList())
|
||||
|
||||
// lets use a mutable variable
|
||||
var ml = arrayList("a").iterator()
|
||||
ml += a.iterator()
|
||||
ml += "beer"
|
||||
ml += b
|
||||
ml += "z"
|
||||
assertEquals(arrayList("a", "foo", "bar", "beer", "cheese", "wine", "z"), ml.toList())
|
||||
}
|
||||
|
||||
test fun requireNoNulls() {
|
||||
val iter = arrayList<String?>("foo", "bar").iterator()
|
||||
val notNull = iter.requireNoNulls()
|
||||
|
||||
Reference in New Issue
Block a user