简体   繁体   中英

Converting an Array of Hexadecimal Strings to Numbers

I have an application in which a server is sending a lot of data every second to clients that request it. In this data set are several (large) arrays that contain numbers (in some cases 16-bit integers and in others double precision floats). In order to reduce the packet size, I would like to send only the number of bytes that are necessary to represent the number (2 bytes for the 16 bit and 8 for the 64 bit). I know that I can do something like this:

/* Create space for 4 32 bit numbers */
var buffer = new ArrayBuffer(16);

/* Hex representation of [0, 123, 246, 369] */
buffer = ["0x0", 0x7B", "0xF6", "0x171"];

/* Actual array containing numbers above */
var int32View = new Int32Array(buffer); 

but....I don't want to prepend everything sting with "0x" (adding two bytes will double the size of the 16 bit numbers). I think I might be missing something - is there a better way to do this such that I don't need to indicate that the strings are hexadecimal representations of numbers (ie can I drop the "0x")?

Thanks, Matt

You can use map() or a for-loop to treat each value and use the length as basis for where to sort them out.

One note though, you mention 64-bit floats. When these are extracted from a buffer they will be 64-bit integer values (ie. 0xXXXXXXXXXXXXXXXX) formatted in IEEE-754 format.

However, JavaScript can only work with 32-bit values (0xXXXXXXXX) so you have to split the processing of those into two parts using a 32-bit unsigned array, then add a Float64Array view for that later.

If the float values are literals, ie "2.345", "-1.33" etc. then you can simply use parseFloat(str) on them (instead of handling 64-bit values as below).

Example

 // inserted 64-bit IEEE float of -2.3357 = 0x7b4a233ac002af83 var normArray = ["0", "7B", "F6", "7b4a233ac002af83", "171"], int16a = [], int32a = [], int16b, int32b, float64b; normArray.map(function(entry) { if (entry.length > 4) { var high = entry.substr(0, 8), low = entry.substr(8, 8); int32a.push(parseInt(high, 16), parseInt(low, 16)); } else { int16a.push(parseInt(entry, 16)); } }); // convert to typed arrays int16b = new Int16Array(int16a); int32b = new Uint32Array(int32a); float64b = new Float64Array(int32b.buffer); // convert IEEE rep. to floats document.writeln("<pre>int16 : " + int16b[0] + ", " + int16b[1] + ", " + int16b[2] + ", ..."); document.write("float64: " + float64b[0] + "</pre>") 

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM