Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Convert byte array to hex string

Tags:

ruby

I am trying to convert the following byte array to hexadecimal;

[1, 1, 65, -50, 6, 104, -91, -70, -100, 119, -100, 123, 52, -109, -33, 45, -14, 86, -105, -97, -115, 16]

The result should be;

010141CE0668A5BA9C779C7B3493DF2DF256979F8D10

Here is my current attempt;

item.getProperties["Mapi-Conversation-Index"].to_a.map {|s| s.to_s(16)}.join()

But my output is: 010141-320668-5b-46-6477-647b34-6d-212d-e56-69-61-7310

like image 303
Sam Avatar asked Dec 03 '22 11:12

Sam


2 Answers

arr = [1, 1, 65, -50, 6, 104, -91, -70, -100, 119, -100, 123, 52, -109, -33, 45, -14, 86]

arr.pack("c*").unpack("H*").first
  #=> "010141ce0668a5ba9c779c7b3493df2df256"  

See Array#pack and String#unpack.

The argument "c" for pack specifies an 8-bit signed integer. The argument "H" for unpack specifies "hex string (high nibble first)". The asterisk at the end of each directive specifies that "c" applies to all elements of arr and "H" applies to all characters of the string produced by pack.

Note that

arr.pack("c*")
  #=> "\x01\x01A\xCE\x06h\xA5\xBA\x9Cw\x9C{4\x93\xDF-\xF2V"

and

arr.pack("c*").unpack("H*")
  #=> ["010141ce0668a5ba9c779c7b3493df2df256"]

which is why first is needed to extract the string.

like image 198
Cary Swoveland Avatar answered Dec 22 '22 19:12

Cary Swoveland


This works:

[1, 1, 65, -50].map { |n| '%02X' % (n & 0xFF) }.join

The %02X format specifier makes a 2-character-wide hex number, padded with 0 digits. The & 0xFF is necessary to convert your negative numbers into the standard 0 through 255 range that people usually use when talking about byte values.

like image 22
David Grayson Avatar answered Dec 22 '22 19:12

David Grayson