2012-09-18 97 views
1

我有我从套接字读取数据时,我知道它的格式如下:获取十六进制值,并转换为十进制

[2字节] [8个字节] [2字节] = 12个字节

我想单独阅读;并且值以十六进制表示。其实我捕获数据前一阵子在PHP,并将其保存到文件,我可以用OD(UNIX)正常查看:

$ od -h myFile 
$ 0000000 02eb 02fe fe02 fefe 02fe 02fe 000a 
$ 0000015 

也就是说,有CR和LF底,导致14个字节。 如何从套接字中读取Java中的这些值?例如,如何获得“02eb”(2个字节)并将其转换为十进制值?

我已经从插座上看书,我想最后一件事是:

mMessage = mBRin.readLine(); 
byte[] bytes = mMessage.trim().getBytes() 

但是,让我在数组中18个字节。

如果有帮助,在PHP中拿到第一部分我做:

$input = socket_read($value,13,PHP_BINARY_READ); 
$trim_input = trim($input); 
$float_head = hexdec(bin2hex(substr($input,0,2))); 

我觉得我不理解this,这可能是答案

+0

这些值是二进制的。你用十六进制打印它们。 – EJP

+0

我不确定你的意思,@EJP但是用十六进制打印他们我得到了他们应该是的。你的意思是插座读数? – quinestor

回答

2

我有我从套接字读取数据时,我知道它有以下 格式:

[2字节] [8个字节] [2字节] = 12个字节

如果您已经有了从套接字读取字节的代码,则可以使用ByteBuffer将字节转换为short,int,long等值。

Socket s = .....; 

InputStream in = s.getInputStream(); 
byte [] buf = new byte[12]; 

// read 12 bytes from socket into bytes 
in.read(buf); 

ByteBuffer bb = ByteBuffer.allocate(buf.length); 
bb.order(ByteOrder.LITTLE_ENDIAN); 
bb.put(buf); 
bb.flip(); 
short short1 = bb.getShort(); 
long long1 = bb.getLong(); 
short short2 = bb.getShort(); 

请注意将字节缓冲区设置为little endian的调用。

当您执行od命令时,您的输出与以下内容类似(此输出来自我在系统上创建的文件以模拟您的文件)。 od -h命令读取文件中的字节,将它们放在一起作为2字节的short ends模式,然后以十六进制打印出短值。

$ od -h binary.dat 
0000000  02eb 02fe fe02 fefe 02fe 02fe 000a   
0000015 

但是,如果您使用-tx1,您会看到字符按它们在文件中出现的实际顺序排列。

$ od -tx1 binary.dat 
$ 0000000 eb 02 fe 02 02 fe fe fe fe 02 fe 02 0a 
$ 0000015 

如果您在文件上运行此我想你会发现它真的是13个字节不是14个字节,由单一的LF,而不是CRLF终止。您看到的“额外”字节是od -h中的“present”,实际上并不存在于文件中。

无论如何,第一个字节是值235(十六进制EB)。第二个字节是2.问题是 - 对于第一个短的想要什么是正确的值。如果根据您的套接字协议,数据以小端模式进行串行化,那么这两个字节的值连接成一个简短的值是02EB十六进制或747。如果套接字协议使用big endian,则值为EB02(十六进制)或60162.

ByteBuffer方法为您提供了灵活性,并允许您以big-endian或little endian进行读取/写入。它还允许将读取的数据从套接字(字节数组)中分离出来,然后再将数据转换为数字。这可能使单元测试更容易,因为您可以为各种测试用例创建字节数组,并确保您的解析代码按预期工作。

sharadendu的答案DataInputStream方法也将工作 - 但只有当套接字协议是big-endian。 DataInputStream被硬编码为big-endian。

+0

谢谢你的回答,sharadendu的回答我可以看到值,但用你的方法,我看到不正确的值。我觉得这是答案..你是否尝试过自己写的东西?我正确加载buf,已经简单购买short1 = bb.getShort();我得到的值不等于short f1 = dis.readShort(); – quinestor

+0

哦,我认为问题来自于getBytes,因为从那里得到的数组是19字节 – quinestor

+0

将bb.order(ByteOrder.LITTLE_ENDIAN)更改为bb.order(ByteOrder.BIG_ENDIAN),我的代码片段将产生与DataInputStream示例。你的例子让我觉得数据是小端的。如果DataInputStream返回期望值,那么你的数据流是big endian –

2
Socket socket = ......; 
     DataInputStream dis = new DataInputStream(socket.getInputStream()); 
     short f1 = dis.readShort(); 
     long f2 = dis.readLong(); 
     sort f3 = dis.readShort(); 

要打印的值十六进制使用String.format(“%x”,f1); 希望它可以帮助...

+0

谢谢,这就是它。 +1我已经可以理解,不需要十进制转换,因为长整数和短整数是一致的。我在等待user1657364的回答,因为它更一般 – quinestor

相关问题