Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Read structured data from binary file -?

I know the file structure, suppose this structure is this:

[3-bytes long int],[1-byte long unsigned integer],[4-bytes long unsigned integer]

So the file contains chains of such records.

What is the most elegent way to parse such a file in Java?

Supposedly, we can define a byte[] array of overall length and read it with InputStream, but how then convert its subelements into correct integer values?

First thing, byte value in java is signed, we need unsigned value in our case. Next thing, are there useful methods that allow to convert a sub-array of bytes, say, bytes from 1-st to 4-th into a correct integer value?

I know for sure, there are functions pack & unpack in Perl, that allow you to represent a string of bytes as an expression, let's say "VV" means 2 unsigned long int values. You define such a string and provide it as an argument to a pack or unpack functions, along with the bytes to be packed/unpacked. Are there such things in Java / Apache libs etc ?

like image 343
EugeneP Avatar asked Jul 14 '10 04:07

EugeneP


1 Answers

Like @Bryan Kyle example but shorter. I like shorter, but that doesn't mean clearer, you decide. ;) Note: readByte() is signed and will have unexpected results if not masked with 0xFF.

DataInputStream dis = ... 

// assuming BIG_ENDIAN format
int a = dis.read() << 16 | dis.read() << 8 | dis.read(); 
short b = (short) dis.read(); 
long c = dis.readInt() & 0xFFFFFFFFL; 

or

ByteBuffer bb = 
bb.position(a_random_postion);
int a = (bb.get() & 0xFF) << 16 | (bb.get() & 0xFF) << 8 | (bb.get() & 0xFF); 
short b = (short) (bb.get() & 0xFF); 
long c = bb.readInt() & 0xFFFFFFFFL; 
like image 185
Peter Lawrey Avatar answered Oct 06 '22 12:10

Peter Lawrey