CompoundByteIteratorBase.coffee | |
---|---|
ByteIterator = (require '../../database/ByteIterator.coffee').ByteIterator
ByteIterable = (require '../../database/ByteIterable.coffee').ByteIterable
Addr64 = (require '../Addr64.coffee').Addr64
LogUtil = (require '../LogUtil.coffee').LogUtil
ExodusError = (require '../../util/ExodusVersion.coffee').ExodusError | |
This class allows working with several iterators (one after another). | class CompoundByteIteratorBase extends ByteIterator |
@private | private: undefined |
@private | hasNext: undefined |
@private | hasNextValid: undefined |
@protected Constructor. @param current the base iterator. | @create$ByteIterator: (current, o) ->
if !o? then o = new CompoundByteIteratorBase
o.current = current
return o |
@protected Constructor. | @create: (o) ->
return CompoundByteIteratorBase.
create$ByteIterator ByteIterable.EMPTY_ITERATOR, o |
Check whether there is next element. @return true or false. | hasNext$emit: () ->
onHasNextImpl = (@hasNext) =>
@hasNextValid = true
@once 'hasNextImpl', (hasNext) =>
onHasNextImpl hasNext
@emit 'hasNext', hasNext
if !@hasNextValid
@hasNext = @hasNextImpl$emit()
if @hasNext?
@removeAllListeners 'hasNextImpl'
onHasNextImpl @hasNext
return @hasNext
else
return undefined
return @hasNext |
Skip several elements. @param length the number of elements to skip. @return the number of elements actually skipped. | skip$int: (length) ->
skipped = @current.skip$int length
while true
@hasNextValid = false
if skipped >= length || !@hasNext$emit()
break
skipped += @current.skip$int(length - skipped)
return skipped |
Get next element. @return next element. | next$emit: () ->
if !@hasNext$emit()
@onFail$String "CompoundByteIterator: no more bytes available"
@current.once 'next', (result) =>
@hasNextValid = false
@emit 'next', result
result = @current.next$emit()
if result?
@current.removeAllListeners 'next'
@hasNextValid = false
return result
else
return undefined |
@private | hasNextImpl$emit: () ->
cycleStep = () =>
@once 'nextIterator', (nextIterator) =>
emit = true
onNextIterator nextIterator
nextIterator = @nextIterator$emit()
if nextIterator?
@removeAllListeners 'nextIterator'
return onNextIterator nextIterator
else
return undefined
onNextIterator = (nextIterator) =>
if !nextIterator?
if emit
@emit 'hasNextImpl$emit', false
else
return false
@current = nextIterator
if !@current.hasNext$emit()
cycleStep()
if emit
@emit 'hasNextImpl$emit', true
else
return true
emit = false
if !@current? || !@current.hasNext$emit()?
cycleStep()
return true
getCurrent: () ->
return @current |
@protected Throws error message. @param message. | onFail$String: (message) ->
throw new ExodusError(message) |
TEMPORARY!!! Get buffer with data at current position. @param length the length of data to be read. @return buffer with data or undefined. Behavour is similar to getValue. | getData$int$emit: (length, cache) ->
if !@cache? then @cache = cache
b = new Buffer length
k = Math.ceil((@offset + length) / @cache.getPageSize())
buffers = new Object()
pagesRead = 0
onGetPage = (addrStr, buffer) =>
buffers[addrStr] = buffer
pagesRead += 1
if pagesRead == k
for i in [0..k - 1]
pageAddr = @pageAddr.plus$int(i * @cache.getPageSize())
addrStr = Addr64.addr64ToString$Addr64$int(pageAddr,
LogUtil.LOG_NAME_BASE)
if buffers[addrStr]?
buffer = buffers[addrStr]
if i == 0
buffer.copy b, 0, @offset, Math.min(@cache.getPageSize(),
@offset + length)
else if i < k - 1
buffer.copy b, i * @cache.getPageSize() - @offset, 0,
@cache.getPageSize()
else
buffer.copy b, i * @cache.getPageSize() - @offset, 0,
(length + @offset) % @cache.getPageSize()
@emit 'getData', b
for i in [0..k - 1]
pageAddr = @pageAddr.plus$int(i * @cache.getPageSize())
addrString = Addr64.addr64ToString$Addr64$int(pageAddr,
LogUtil.LOG_NAME_BASE)
@cache.once 'getPage' + addrString, (buffer, addrStr) =>
onGetPage addrStr, buffer
buffer = @cache.getPage$Addr64$emit pageAddr
if buffer?
pagesRead += 1
if i == 0
buffer.copy b, 0, @offset, Math.min(@cache.getPageSize(),
@offset + length)
else if i < k - 1
buffer.copy b, i * @cache.getPageSize() - @offset, 0,
@cache.getPageSize()
else
buffer.copy b, i * @cache.getPageSize() - @offset, 0,
(length + @offset) % @cache.getPageSize()
if pagesRead == k
return b
else
return undefined
exports.CompoundByteIteratorBase = CompoundByteIteratorBase
|