public class NodeSerializer extends Object
An instance of this class is used to serialize and de-serialize the
INodeData
s and ILeafData
s of an AbstractBTree
. Leaf
and non-leaf records have different serialization formats, but their leading
bytes use the same format so that you can tell by inspection whether a buffer
contains a leaf or a non-leaf node. The header of the record uses a fixed
length format so that some fields can be tested without full
de-serialization, especially whether the record contains a leaf vs a node.
This fixed record also makes it possible to update some fields in the header
once the entire record has been serialized, including the checksum, the #of
bytes in the serialized record, and the prior/next addresses for leaves.
The methods defined by this class all work with ByteBuffer
s. On read,
the buffer must be positioned to the start of the data to be read. After a
read, the buffer will be positioned to the first byte after the data read. If
there is insufficient data available in the buffer then an
BufferUnderflowException
will be thrown. On write, the data will be
written on an internal buffer whose size is automatically extended. The write
buffer is reused for each write and quickly achieves a maximum size for any
given BTree
.
Note: while the NodeSerializer
is NOT thread-safe for writers, it is
thread-safe for readers. This design mirrors the concurrency capabilities of
the AbstractBTree
.
AbstractBTree
,
IndexMetadata
,
IAbstractNodeData
,
IAbstractNodeDataCoder
Modifier and Type | Field and Description |
---|---|
static int |
DEFAULT_BUFFER_CAPACITY_PER_ENTRY
The default initial capacity multiplier for the (de-)serialization buffer.
|
protected INodeFactory |
nodeFactory
|
Constructor and Description |
---|
NodeSerializer(IAddressManager addressManager,
INodeFactory nodeFactory,
int branchingFactor,
int initialBufferCapacity,
IndexMetadata indexMetadata,
boolean readOnly,
IRecordCompressorFactory<?> recordCompressorFactory)
Designated constructor.
|
Modifier and Type | Method and Description |
---|---|
void |
close()
Releases any buffers.
|
IAbstractNodeData |
decode(ByteBuffer buf)
|
AbstractFixedByteArrayBuffer |
encode(IAbstractNodeData node)
Deprecated.
This method is no longer used since I refactored the
IndexSegmentBuilder to optionally stuff the generated
nodes and leaves into the cache. It still works but it might
go away in the future. |
<T extends IAbstractNodeData> |
encodeLive(T node)
Encode a node or leaf and return a coded instance of the persistent data
for that node or leaf backed by an exact fit byte[] (NOT thread-safe).
|
void |
updateLeaf(ByteBuffer b,
long priorAddr,
long nextAddr)
Update the serialization of a leaf to set the prior and next leaf
references and change its serialization type from
#TYPE_LEAF to
#TYPE_LINKED_LEAF . |
AbstractNode<?> |
wrap(AbstractBTree btree,
long addr,
IAbstractNodeData data)
|
protected final INodeFactory nodeFactory
public static final transient int DEFAULT_BUFFER_CAPACITY_PER_ENTRY
#branchingFactor
.public NodeSerializer(IAddressManager addressManager, INodeFactory nodeFactory, int branchingFactor, int initialBufferCapacity, IndexMetadata indexMetadata, boolean readOnly, IRecordCompressorFactory<?> recordCompressorFactory)
nodeFactory
- An object that knows how to construct INodeData
s and
leaves
.branchingFactor
- The branching factor for target B+Tree. For the
IndexSegmentBuilder
this should be the branching
factor of the IndexSegment
which is being generated.
Otherwise it is the branching factor of the
AbstractBTree
itself.initialBufferCapacity
- The initial capacity for internal buffer used to serialize
nodes and leaves. The buffer will be resized as necessary
until it is sufficient for the records being serialized for
the BTree
. When zero (0), a default is used. A
non-zero value is worth specifying only when the actual buffer
size is consistently less than the default for some
BTree
. See DEFAULT_BUFFER_CAPACITY_PER_ENTRY
indexMetadata
- The IndexMetadata
record for the index.readOnly
- true
IFF the caller is asserting that they WILL
NOT attempt to serialize any nodes or leaves using this
NodeSerializer
instance.
FIXME IRecordCompressorFactory
should either be used
here or moved into the IRawStore
impl.public void close()
NodeSerializer
is used again.public IAbstractNodeData decode(ByteBuffer buf)
INodeData
or ILeafData
record, wrapping the
underlying data record (thread-safe). The decision to decode as an
INodeData
or ILeafData
instance is made based on
inspection of the first byte byte in the supplied buffer, which codes for
a node, leaf, or linked-leaf.buf
- The data record.INodeData
or ILeafData
instance for that data
record.
FIXME modify to accept IDataRecord
rather than
ByteBuffer
.public AbstractNode<?> wrap(AbstractBTree btree, long addr, IAbstractNodeData data)
INodeData
or ILeafData
instance as a Node
or a Leaf
. This DOES NOT set the parent of the new Node
or Leaf
.btree
- The owning B+Tree.addr
- The address of the data record in the backing store.data
- The data record.public <T extends IAbstractNodeData> T encodeLive(T node)
node
- The node or leaf.public AbstractFixedByteArrayBuffer encode(IAbstractNodeData node)
IndexSegmentBuilder
to optionally stuff the generated
nodes and leaves into the cache. It still works but it might
go away in the future.encodeLive(IAbstractNodeData)
which is used when the written
node or leaf will not be reused, e.g., by the IndexSegmentBuilder
. The operation writes on an internal buffer which is automatically
extended as required.node
- The node or leaf.public void updateLeaf(ByteBuffer b, long priorAddr, long nextAddr)
#TYPE_LEAF
to
#TYPE_LINKED_LEAF
.
Note: In order to use this method to write linked leaves on the store you have to either write behind at a pre-determined address on the store or settle for writing only the prior or the next leaf address, but not both. It is up to the caller to perform these tricks. All this method does is to touch up the serialized record.
Note: This method has NO side-effects on the position or
limit of the caller's ByteBuffer
.
b
- The serialization leaf.priorAddr
- The address of the previous leaf in key order, 0L
if it is known that there is no previous leaf, and
-1L
if either: (a) it is not known whether there
is a previous leaf; or (b) it is known but the address of that
leaf is not known to the caller.nextAddr
- The address of the next leaf in key order, 0L
if
it is known that there is no next leaf, and -1L
if either: (a) it is not known whether there is a next leaf;
or (b) it is known but the address of that leaf is not known
to the caller.IndexSegmentBuilder
,
DefaultLeafCoder
Copyright © 2006–2019 SYSTAP, LLC DBA Blazegraph. All rights reserved.