aboutsummaryrefslogblamecommitdiffstats
path: root/Godeps/_workspace/src/github.com/syndtr/goleveldb/leveldb/iterator/array_iter.go
blob: 9b4b72741b5038a17ddc57640b8ba242e61ce7b3 (plain) (tree)





























































































































































                                                                              
// Copyright (c) 2014, Suryandaru Triandana <syndtr@gmail.com>
// All rights reserved.
//
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

package iterator

import (
    "github.com/syndtr/goleveldb/leveldb/util"
)

// BasicArray is the interface that wraps basic Len and Search method.
type BasicArray interface {
    // Len returns length of the array.
    Len() int

    // Search finds smallest index that point to a key that is greater
    // than or equal to the given key.
    Search(key []byte) int
}

// Array is the interface that wraps BasicArray and basic Index method.
type Array interface {
    BasicArray

    // Index returns key/value pair with index of i.
    Index(i int) (key, value []byte)
}

// Array is the interface that wraps BasicArray and basic Get method.
type ArrayIndexer interface {
    BasicArray

    // Get returns a new data iterator with index of i.
    Get(i int) Iterator
}

type basicArrayIterator struct {
    util.BasicReleaser
    array BasicArray
    pos   int
}

func (i *basicArrayIterator) Valid() bool {
    return i.pos >= 0 && i.pos < i.array.Len()
}

func (i *basicArrayIterator) First() bool {
    if i.array.Len() == 0 {
        i.pos = -1
        return false
    }
    i.pos = 0
    return true
}

func (i *basicArrayIterator) Last() bool {
    n := i.array.Len()
    if n == 0 {
        i.pos = 0
        return false
    }
    i.pos = n - 1
    return true
}

func (i *basicArrayIterator) Seek(key []byte) bool {
    n := i.array.Len()
    if n == 0 {
        i.pos = 0
        return false
    }
    i.pos = i.array.Search(key)
    if i.pos >= n {
        return false
    }
    return true
}

func (i *basicArrayIterator) Next() bool {
    i.pos++
    if n := i.array.Len(); i.pos >= n {
        i.pos = n
        return false
    }
    return true
}

func (i *basicArrayIterator) Prev() bool {
    i.pos--
    if i.pos < 0 {
        i.pos = -1
        return false
    }
    return true
}

func (i *basicArrayIterator) Error() error { return nil }

type arrayIterator struct {
    basicArrayIterator
    array      Array
    pos        int
    key, value []byte
}

func (i *arrayIterator) updateKV() {
    if i.pos == i.basicArrayIterator.pos {
        return
    }
    i.pos = i.basicArrayIterator.pos
    if i.Valid() {
        i.key, i.value = i.array.Index(i.pos)
    } else {
        i.key = nil
        i.value = nil
    }
}

func (i *arrayIterator) Key() []byte {
    i.updateKV()
    return i.key
}

func (i *arrayIterator) Value() []byte {
    i.updateKV()
    return i.value
}

type arrayIteratorIndexer struct {
    basicArrayIterator
    array ArrayIndexer
}

func (i *arrayIteratorIndexer) Get() Iterator {
    if i.Valid() {
        return i.array.Get(i.basicArrayIterator.pos)
    }
    return nil
}

// NewArrayIterator returns an iterator from the given array.
func NewArrayIterator(array Array) Iterator {
    return &arrayIterator{
        basicArrayIterator: basicArrayIterator{array: array, pos: -1},
        array:              array,
        pos:                -1,
    }
}

// NewArrayIndexer returns an index iterator from the given array.
func NewArrayIndexer(array ArrayIndexer) IteratorIndexer {
    return &arrayIteratorIndexer{
        basicArrayIterator: basicArrayIterator{array: array, pos: -1},
        array:              array,
    }
}