Reputation: 1092
I am trying to find java equivalent for python's
struct.unpack('hccccc',raw)
https://docs.python.org/2/library/struct.html
How can I do this in a clean way?
Upvotes: 4
Views: 6983
Reputation: 142
I stuck with a similar task today, while I was tuning a murmur splitting hash function. So may be it will be useful for someone.
For struct.unpack('q', msg)[0]
you can use ByteBuffer.wrap(msg.getBytes()).order(ByteOrder.LITTLE_ENDIAN).getLong();
because "q" is 'long long' has size -(1<<63) to (1<<63)-1 (-9,223,372,036,854,775,808 to 9,223,372,036,854,775,807) in C++ (8 bytes) that is equal 'long' in Java (8 bytes) which has also "-9,223,372,036,854,775,808 to 9,223,372,036,854,775,807".
Upvotes: 0
Reputation: 873
JBBP library can help in the case
byte [] data = new byte [] {1,2,3,4,5,6,7,8};
JBBPFieldStruct parsed = JBBPParser.prepare("short; ubyte [5];").parse(new ByteArrayInputStream(data));
System.out.println("short = "+parsed.findFieldForType(JBBPFieldShort.class).getAsInt());
System.out.println("array = "+Arrays.toString(parsed.findFieldForType(JBBPFieldArrayUByte.class).getArray()));
Upvotes: 2
Reputation: 1092
This is how I handled to do that, I don't think/know if its the best way to do it but after many searchs I made my own, I might be making an actual and complete/clean api for doing that. if I do so I will post it here
x stands for ignore
c for char
s for string
b for byte
import java.nio.*;
public class struct{
public static String[] unpack(char[] packet, byte[] raw){
String[] result = new String[packet.length];
int pos = 0;
int Strindex = 0;
for (int x = 0; x < packet.length; x++){
char type = packet[x];
if (type == 'x'){
pos += 1;
continue;
}
else if (type == 'c'){
char c = (char) (raw[pos] & 0xFF);
result[Strindex] = Character.toString(c);
Strindex += 1;
pos += 1;
}
else if (type == 'h'){
ByteBuffer bb = ByteBuffer.allocate(2);
bb.order(ByteOrder.LITTLE_ENDIAN);
bb.put(raw[pos]);
bb.put(raw[pos+1]);
short shortVal = bb.getShort(0);
result[Strindex] = Short.toString(shortVal);
pos += 2;
Strindex += 1;
}
else if (type == 's'){
String s = "";
while (raw[pos] != (byte)0x00){
char c = (char) (raw[pos] & 0xFF);
s += Character.toString(c);
pos += 1;
}
result[Strindex] = s;
Strindex += 1;
pos += 1;
}
else if (type == 'b'){
Byte p = raw[pos];
result[Strindex] = Integer.toString(p.intValue());
Strindex += 1;
pos += 1;
}
}
return result;
}
}
Upvotes: 1
Reputation: 36987
This kind of operation is called "Serialization" in Java. See http://www.tutorialspoint.com/java/java_serialization.htm for a tutorial. Since serialization works with bytes, not characters, you might want to encode those bytes afterwards to get a printable string.
Upvotes: 0