我有一个这样的班级:
public class Fields implements java.io.Serializable{
public short ID;
public int SSN;
public long Number;
}
,我有一个十六进制字符串,其值像这样,每个2个字符代表一个字节:
String str="1000180018000540AC80D6487653E5000100D40B7900D4C3FFF2FAFF8985";
现在,我想以这种模式将此字符串转换为上述类对象:
//ID has short type so we need 2 bytes
ID=4096; //(decimal value of 1000)
//SSN has integer type so we need 4 bytes
SSN=402659328; //(decimal value of 18001800)
//Number has long type so we need 8 bytes
Number=378492038049986131; //(decimal value of 0540AC80D6487653)
可以使用<reinterpret_cast>
在c ++中轻松实现这种转换,但是正如所说的Is there cast in Java similar to in C++问题,我可以在Java中使用序列化来实现。我认为,当我们首先将一个类对象序列化为字节数组时,可以使用序列化,然后我们可以将获得的字节反序列化为原始类对象,这与我的建议有点不同,因为我有一个字符串(例如字节),我想对此进行反序列化。那我该怎么办呢?
答案 0 :(得分:4)
Java序列化具有非常特殊的数据格式,它不能帮助您解析使用其他预定义格式获得的数据。但是a ByteBuffer
在解析此类数据时可能很有用。
首先,您需要将字符串转换为实际的byte[]
数组。我将使用this answer中的一个简单解决方案,随时选择另一个更适合您的示例的解决方案:
byte[] data = DatatypeConverter.parseHexBinary(str);
ByteBuffer buffer = ByteBuffer.wrap(data);
buffer.order(ByteOrder.LITTLE_ENDIAN); // maybe!
short id = buffer.getShort();
int ssn = buffer.getInt();
long number = buffer.getLong();
是否需要进行order()
调用取决于数据所在的字节序。ByteBuffer
默认为BIG_ENDIAN
,因此如果需要,可以将其省略
答案 1 :(得分:3)
我认为<reinterpret_cast>
不会奏效。 "1000"
的内部字节表示是4个ASCII字节。一个用于字符1
(0x31
),然后是3个字符0
(0x30
),而不是十六进制的0x10, 0x00
。您将在id
与<reinterpret_cast>
中得到的结果将是十六进制0x31303030
而不是0x1000
。
您需要做的是解析字符串的不同组成部分。
类似的事情应该做:
int id = Integer.parseInt(str.substring(0,4), 16);
答案 2 :(得分:2)
您只需要split
和parse
public Fields(String str) {
ID = Short.parseShort(str.substring(0, 4), 16);
SSN = Integer.parseInt(str.substring(4, 12), 16);
Number = Long.parseLong(str.substring(12, 28), 16);
}