|
||||||||||
PREV CLASS NEXT CLASS | FRAMES NO FRAMES | |||||||||
SUMMARY: NESTED | FIELD | CONSTR | METHOD | DETAIL: FIELD | CONSTR | METHOD |
java.lang.Objectnet.kano.joscar.ByteBlock
Provides a read-only interface to an underlying block of data. This class
is useful for conserving memory (and CPU time copying memory) when many
objects need to access different parts of a byte array.
For example, when
a FLAP packet is read from a stream, a ByteBlock
is created
containing the FLAP data (bytes 6 through n-6-1, where n is the FLAP data
length). If this is a channel-2 FLAP, then a SnacPacket
is
created, which creates a ByteBlock
representing the SNAC data,
or bytes 10 through n-10-1 of the FLAP data. Then, if this command is an
ICBM (like an IM or chat message), an AbstractIcbmCommand
subclass creates another ByteBlock
to represent the
"channel-specific data," and in most cases the channel data are read as
a TlvChain
, which splits that ByteBlock
up into,
in the case of IM, up to five separate TLV
's, each containing
a ByteBlock that represents some range of data within that
TlvChain
.
Now obviously it would be inefficient to be copying the majority of each IM
packet's data at least four times. On the other hand, it would be tedious to
pass an offset into the array and a length to every single method that needed
some part of every packet that came in. Thus, ByteBlock
was
created, providing the convenience of a single object to represent data
with the efficiency of accessing a single underlying byte[]
,
and with the added security of being immutable (that is, read-only).
Field Summary | |
static ByteBlock |
EMPTY_BLOCK
A ByteBlock with a length of 0. |
Method Summary | |
void |
copyTo(byte[] dest,
int destOffset)
Copies the data in this block to the given array at the given position. |
static ByteBlock |
createByteBlock(LiveWritable writable)
Creates a ByteBlock by writing the given
LiveWritable to a byte array, then wrapping that array in a ByteBlock .
|
static ByteBlock |
createByteBlock(LiveWritable[] writables)
Creates a ByteBlock by concatenating the output of the given
list of LiveWritable s. |
static java.io.InputStream |
createInputStream(ByteBlock data)
Returns an InputStream that simply reads from the given byte
block. |
static java.lang.String |
createString(ByteBlock block,
java.lang.String charset)
Creates a String from the data in the given block, using
the given charset for encoding. |
boolean |
equals(java.lang.Object o)
Returns true if this and the given object represent the same
data, byte for byte; false otherwise. |
byte |
get(int index)
Returns the byte in this block at the given index. |
int |
getLength()
Returns the length of this byte block. |
int |
getOffset()
Returns the offset into the backing array that represents the first index of this block. |
long |
getWritableLength()
Provided in order to satisfy the requirements of Writable ;
returns the length of this byte block. |
int |
hashCode()
|
ByteBlock |
subBlock(int offset)
Returns a new ByteBlock containing all bytes in this block
from offset to the end of this block. |
ByteBlock |
subBlock(int offset,
int len)
Returns a new ByteBlock containing the first
len bytes in this block starting at index
offset .
|
byte[] |
toByteArray()
Allocates a new byte array containing a copy of the contents of this byte block. |
java.lang.String |
toString()
|
static ByteBlock |
wrap(byte[] bytes)
Returns a ByteBlock logically equivalent to the given byte array. |
static ByteBlock |
wrap(byte[] bytes,
int offset)
Creates a ByteBlock that is simply a wrapper around the
data in the given array after the given index. |
static ByteBlock |
wrap(byte[] bytes,
int offset,
int len)
Creates a ByteBlock that is simply a wrapper around the
specified length of data in the given array after the given index. |
void |
write(java.io.OutputStream stream)
Writes the contents of this ByteBlock to the given stream. |
Methods inherited from class java.lang.Object |
clone, finalize, getClass, notify, notifyAll, wait, wait, wait |
Field Detail |
public static final ByteBlock EMPTY_BLOCK
ByteBlock
with a length of 0.
Method Detail |
public static ByteBlock wrap(byte[] bytes) throws java.lang.IllegalArgumentException
ByteBlock.wrap(bytes, 0,
bytes.length)
.
ByteBlock
class is described as
"immutable" because there are no public methods that can modify the
object's state, there is still the possibility that anyone with a
reference to the given byte[]
will still be able to modify
its contents. Thus, ByteBlock
is, in a sense, only as
immutable as you make it.
bytes
- the data to "wrap" in the ByteBlock
ByteBlock
backed by the given array
java.lang.IllegalArgumentException
- if the given byte array is
null
wrap(byte[], int, int)
public static ByteBlock wrap(byte[] bytes, int offset) throws java.lang.IllegalArgumentException, java.lang.IndexOutOfBoundsException
ByteBlock
that is simply a wrapper around the
data in the given array after the given index. Thus,
ByteBlock.wrap(bytes, 50).get(0) == bytes[50]
, and
ByteBlock.wrap(bytes, 50).getLength() == (bytes.length -
50)
.
ByteBlock.wrap(bytes, offset, bytes.length
- offset)
.
ByteBlock
class is described as
"immutable" because there are no public methods that can modify the
object's state, there is still the possibility that anyone with a
reference to the given byte[]
will still be able to modify
its contents. Thus, ByteBlock
is, in a sense, only as
immutable as you make it.
bytes
- the data that the returned ByteBlock
will
containoffset
- the starting index of the data to be held in the returned
ByteBlock
ByteBlock
backed by the given array after the
given index
java.lang.IllegalArgumentException
- if the given array is null
java.lang.IndexOutOfBoundsException
- if the given offset is less than zero
or greater than the given array's lengthwrap(byte[], int, int)
public static ByteBlock wrap(byte[] bytes, int offset, int len) throws java.lang.IllegalArgumentException, java.lang.IndexOutOfBoundsException
ByteBlock
that is simply a wrapper around the
specified length of data in the given array after the given index. Thus,
ByteBlock.wrap(bytes, 50, 3).get(0) == bytes[50]
, and
ByteBlock.wrap(bytes, 50, 3).getLength() == 3
.
ByteBlock
class is described as
"immutable" because there are no public methods that can modify the
object's state, there is still the possibility that anyone with a
reference to the given byte[]
will still be able to modify
its contents. Thus, ByteBlock
is, in a sense, only as
immutable as you make it.
bytes
- the data that the returned ByteBlock
will
containoffset
- the starting index of the data to be held in the returned
ByteBlock
len
- the number of bytes after index
to hold in the
returned ByteBlock
ByteBlock
backed by the given number of bytes
after the given index
java.lang.IllegalArgumentException
- if the given byte array is
null
java.lang.IndexOutOfBoundsException
- if the given offset is less than zero
or greater than the length of the given byte array, or if the
given length is less than zero or greater than the length of
the given array minus the given offset (that is, if offset
+ len > bytes.length
)public static ByteBlock createByteBlock(LiveWritable writable) throws java.lang.ArrayIndexOutOfBoundsException
ByteBlock
by writing the given
LiveWritable
to a byte array, then wrapping that array in a ByteBlock
.
writable
is already a ByteBlock
,
no data will be copied but instead a block backed by the same array and
with the same start index and data length will be created and returned.
writable
- the object to wrap in a ByteBlock
ByteBlock
containing the data written by
writable.write([OutputStream])
java.lang.ArrayIndexOutOfBoundsException
- if
writable.getWritableLength
returns a number larger
than can be stored in an array (n >= Integer.MAX_VALUE
)public static ByteBlock createByteBlock(LiveWritable[] writables) throws java.lang.ArrayIndexOutOfBoundsException
ByteBlock
by concatenating the output of the given
list of LiveWritable
s.
writables
- the list of LiveWritable
s to concatenate
ByteBlock
containing the data output from each
of the given LiveWritable
s, in the given order
java.lang.ArrayIndexOutOfBoundsException
- if the total size is greater than
the maximum size of an array (n >= Integer.MAX_VALUE
)public static java.lang.String createString(ByteBlock block, java.lang.String charset) throws java.io.UnsupportedEncodingException
String
from the data in the given block, using
the given charset for encoding. This is implemented for performance
reasons so that the data need not be copied to a second array to be
converted to a String
.
block
- the block of data to convert to a String
charset
- the charset with which to decode the given data
String
decoded with the given charset from the
given block of data
java.io.UnsupportedEncodingException
- if the given encoding is not
supported by the VMString.String(byte[], int, int, String)
public static java.io.InputStream createInputStream(ByteBlock data)
InputStream
that simply reads from the given byte
block. Semantics of the returned InputStream
are those of
ByteArrayOutputStream
.
data
- the block for which a stream should be created
public final byte get(int index) throws java.lang.IndexOutOfBoundsException
index
- the index of the byte to return
java.lang.IndexOutOfBoundsException
- if the given index is less than zero
or greater than this block's length (getLength()
)public int getLength()
public long getWritableLength()
Writable
;
returns the length of this byte block.
getWritableLength
in interface Writable
public void write(java.io.OutputStream stream) throws java.io.IOException
ByteBlock
to the given stream.
write
in interface Writable
stream
- the stream to which to write this block
java.io.IOException
- if an I/O error occurspublic byte[] toByteArray()
public ByteBlock subBlock(int offset) throws java.lang.IndexOutOfBoundsException
ByteBlock
containing all bytes in this block
from offset
to the end of this block. Calling this method
is the equivalent of calling block.subBlock(offset.getLength() - offset)
.
block.subBlock(5).get(0) ==
block.get(5)
, and block.subBlock(5).getLength() ==
(block.getLength() - 5)
.
offset
- the first index of the data to hold in the new
ByteBlock
ByteBlock
holding all of the bytes in this
block starting at the given offset
java.lang.IndexOutOfBoundsException
public ByteBlock subBlock(int offset, int len) throws java.lang.IndexOutOfBoundsException
ByteBlock
containing the first
len
bytes in this block starting at index
offset
.
block.subBlock(5, 2).get(0) ==
block.get(5)
, and block.subBlock(5, 2).getLength() ==
2
.
offset
- the first index of the data to hold in the new
ByteBlock
len
- the number of bytes that the new ByteBlock
shall
hold
ByteBlock
containing the specified number of
bytes in this block starting at the specified index
java.lang.IndexOutOfBoundsException
- if the specified offset or length is
negative or if offset + length > getLength()
public int getOffset()
b = a.subBlock(50,
2).subBlock(20)
, then b.getOffset() - a.getOffset() ==
70
.
public void copyTo(byte[] dest, int destOffset)
dest
- the array to which to copy this blockdestOffset
- the offset into the given array at which to begin
copying this blockpublic final boolean equals(java.lang.Object o)
true
if this and the given object represent the same
data, byte for byte; false
otherwise.
o
- another ByteBlock
to compare this block to
true
if this block represents the same data as the
given blockpublic final int hashCode()
public java.lang.String toString()
|
||||||||||
PREV CLASS NEXT CLASS | FRAMES NO FRAMES | |||||||||
SUMMARY: NESTED | FIELD | CONSTR | METHOD | DETAIL: FIELD | CONSTR | METHOD |