2

与えられた 3 つの反復子

it1, it2, it3

it1 を反復し、次に it2 を反復し、最後に it3 を反復する 1 つの反復子を返すにはどうすればよいですか?

まあ言ってみれば

def it1 = [1, 2].iterator()
def it2 = [3, 4].iterator()
def it3 = [5, 6].iterator()

返すイテレータが欲しい

1
2
3
4
5
6
4

1 に答える 1

1

私が知っている Groovy のイテレータはありませんが、独自のイテレータを作成できます。

class SequentialIterator<T> implements Iterator<T> {
    List iterators
    int index = 0
    boolean done = false
    T next

    SequentialIterator( Iterator<T> ...iterators ) {
        this.iterators = iterators
        loadNext()
    }

    private void loadNext() {
        while( index < iterators.size() ) {
            if( iterators[ index ].hasNext() ) {
                next = iterators[ index ].next()
                break
            }
            else {
                index++
            }
        }
        if( index >= iterators.size() ) {
            done = true
        }
    }

    void remove() {
        throw UnsupportedOperationException()
    }

    boolean hasNext() {
        !done
    }

    T next() {
        if( done ) {
            throw new NoSuchElementException()
        }
        T ret = next
        loadNext()
        ret
    }
}

def it1 = [1, 2].iterator()
def it2 = [3, 4].iterator()
def it3 = [5, 6].iterator()

assert new SequentialIterator( it1, it2, it3 ).collect() == [ 1, 2, 3, 4, 5, 6 ]

または、貪欲な場合 (同時にすべてのデータをロードする必要がある場合) は、イテレータから順番に値を収集できます。

[ it1, it2, it3 ].collectMany { it.collect() }

または、Dave Newton が言うように、Guava を使用できます。

@Grab( 'com.google.guava:guava:15.0' )
import com.google.common.collect.Iterators

def it1 = [1, 2].iterator()
def it2 = [3, 4].iterator()
def it3 = [5, 6].iterator()

assert Iterators.concat( it1, it2, it3 ).collect() == [ 1, 2, 3, 4, 5, 6 ]

またはコモンズコレクション。

@Grab( 'commons-collections:commons-collections:3.2.1' )
import org.apache.commons.collections.iterators.IteratorChain

def it1 = [1, 2].iterator()
def it2 = [3, 4].iterator()
def it3 = [5, 6].iterator()

assert new IteratorChain( [ it1, it2, it3 ] ).collect() == [ 1, 2, 3, 4, 5, 6 ]
于 2013-10-30T13:56:49.067 に答える