JavaScript:需要函数将包含二进制的字符串转换为十六进制,然后再转换回二进制
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/17204912/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
JavaScript: Need functions to convert a string containing binary to hex, then convert back to binary
提问by user2503552
Lets say I have a string in JavaScript with binary data in it. It may look like this:
假设我在 JavaScript 中有一个字符串,其中包含二进制数据。它可能看起来像这样:
var binary = '00001000010001000101010100001110';
I need some reliable functions to convert this into a hexadecimal string, and then convert back from that hexadecimal to a binary string again. I know about the following functions
我需要一些可靠的函数将其转换为十六进制字符串,然后再次从该十六进制转换回二进制字符串。我知道以下功能
// Convert binary to hexadecimal
var hex = parseInt(binaryCharacters, 2).toString(16);
// Convert hexadecimal to binary
var binary = parseInt(hex, 16).toString(2)
But I'm not sure how to convert the whole string at once. Am I right in understanding I need to convert each 4 binary bits at a time into a single hexadecimal character? Then to get back to binary I loop through each hexadecimal character and convert to binary again?
但我不确定如何一次转换整个字符串。我是否正确理解我需要一次将每个 4 个二进制位转换为单个十六进制字符?然后回到二进制我循环遍历每个十六进制字符并再次转换为二进制?
I have hunted for some simple examples doing this in JavaScript but can't find any.
我在 JavaScript 中寻找了一些简单的例子,但找不到任何例子。
Many thanks
非常感谢
回答by yanhan
The more interesting functions to you are here. Not necessarily the cleanest or most efficient ones, but yea:
对您来说更有趣的功能在这里。不一定是最干净或最有效的,但是是的:
// converts binary string to a hexadecimal string
// returns an object with key 'valid' to a boolean value, indicating
// if the string is a valid binary string.
// If 'valid' is true, the converted hex string can be obtained by
// the 'result' key of the returned object
function binaryToHex(s) {
var i, k, part, accum, ret = '';
for (i = s.length-1; i >= 3; i -= 4) {
// extract out in substrings of 4 and convert to hex
part = s.substr(i+1-4, 4);
accum = 0;
for (k = 0; k < 4; k += 1) {
if (part[k] !== '0' && part[k] !== '1') {
// invalid character
return { valid: false };
}
// compute the length 4 substring
accum = accum * 2 + parseInt(part[k], 10);
}
if (accum >= 10) {
// 'A' to 'F'
ret = String.fromCharCode(accum - 10 + 'A'.charCodeAt(0)) + ret;
} else {
// '0' to '9'
ret = String(accum) + ret;
}
}
// remaining characters, i = 0, 1, or 2
if (i >= 0) {
accum = 0;
// convert from front
for (k = 0; k <= i; k += 1) {
if (s[k] !== '0' && s[k] !== '1') {
return { valid: false };
}
accum = accum * 2 + parseInt(s[k], 10);
}
// 3 bits, value cannot exceed 2^3 - 1 = 7, just convert
ret = String(accum) + ret;
}
return { valid: true, result: ret };
}
// converts hexadecimal string to a binary string
// returns an object with key 'valid' to a boolean value, indicating
// if the string is a valid hexadecimal string.
// If 'valid' is true, the converted binary string can be obtained by
// the 'result' key of the returned object
function hexToBinary(s) {
var i, k, part, ret = '';
// lookup table for easier conversion. '0' characters are padded for '1' to '7'
var lookupTable = {
'0': '0000', '1': '0001', '2': '0010', '3': '0011', '4': '0100',
'5': '0101', '6': '0110', '7': '0111', '8': '1000', '9': '1001',
'a': '1010', 'b': '1011', 'c': '1100', 'd': '1101',
'e': '1110', 'f': '1111',
'A': '1010', 'B': '1011', 'C': '1100', 'D': '1101',
'E': '1110', 'F': '1111'
};
for (i = 0; i < s.length; i += 1) {
if (lookupTable.hasOwnProperty(s[i])) {
ret += lookupTable[s[i]];
} else {
return { valid: false };
}
}
return { valid: true, result: ret };
}
回答by user2503552
Well I found an algorithm herewhich helped explain how to do it. Also this page on Wikipediahelped confirming the 4-bit binary to hexadecimal mappings. I came up with the following code to do it. Other code snippets I found on the web didn't work at all. Let me know if you would make any improvements. You could probably even do a straight lookup table really using that info from Wikipedia which would be faster.
好吧,我在这里找到了一个算法,它有助于解释如何做到这一点。维基百科上的这个页面也帮助确认了 4 位二进制到十六进制的映射。我想出了以下代码来做到这一点。我在网上找到的其他代码片段根本不起作用。让我知道您是否会进行任何改进。你甚至可以使用维基百科中的信息来做一个直接的查找表,这样会更快。
var tools = {
/**
* Converts binary code to hexadecimal string
* @param {string} binaryString A string containing binary numbers e.g. '01001101'
* @return {string} A string containing the hexadecimal numbers
*/
convertBinaryToHexadecimal: function(binaryString)
{
var output = '';
// For every 4 bits in the binary string
for (var i=0; i < binaryString.length; i+=4)
{
// Grab a chunk of 4 bits
var bytes = binaryString.substr(i, 4);
// Convert to decimal then hexadecimal
var decimal = parseInt(bytes, 2);
var hex = decimal.toString(16);
// Uppercase all the letters and append to output
output += hex.toUpperCase();
}
return output;
},
/**
* Converts hexadecimal code to binary code
* @param {string} A string containing single digit hexadecimal numbers
* @return {string} A string containing binary numbers
*/
convertHexadecimalToBinary: function(hexString)
{
var output = '';
// For each hexadecimal character
for (var i=0; i < hexString.length; i++)
{
// Convert to decimal
var decimal = parseInt(hexString.charAt(i), 16);
// Convert to binary and add 0s onto the left as necessary to make up to 4 bits
var binary = this.leftPadding(decimal.toString(2), '0', 4);
// Append to string
output += binary;
}
return output;
},
/**
* Left pad a string with a certain character to a total number of characters
* @param {string} inputString The string to be padded
* @param {string} padCharacter The character that the string should be padded with
* @param {string} totalCharacters The length of string that's required
* @returns {string} A string with characters appended to the front of it
*/
leftPadding: function(inputString, padCharacter, totalCharacters)
{
// If the string is already the right length, just return it
if (!inputString || !padCharacter || inputString.length >= totalCharacters)
{
return inputString;
}
// Work out how many extra characters we need to add to the string
var charsToAdd = (totalCharacters - inputString.length)/padCharacter.length;
// Add padding onto the string
for (var i = 0; i < charsToAdd; i++)
{
inputString = padCharacter + inputString;
}
return inputString;
}
};
回答by Giancarlo Sportelli
Why not using Array.prototype.reduce?
为什么不使用Array.prototype.reduce?
var binstr = "00001000010001000101010100001110"
function bin2hex(b) {
return b.match(/.{4}/g).reduce(function(acc, i) {
return acc + parseInt(i, 2).toString(16);
}, '')
}
function hex2bin(h) {
return h.split('').reduce(function(acc, i) {
return acc + ('000' + parseInt(i, 16).toString(2)).substr(-4, 4);
}, '')
}
console.log(binstr);
> 00001000010001000101010100001110
console.log(bin2hex(binstr));
> 0844550e
console.log(hex2bin(bin2hex(binstr)));
> 00001000010001000101010100001110
Link to jsfiddle here.
链接到 jsfiddle在这里。
Notes:
笔记:
- In
bin2hex
, if you want to convert also trailing chunks of less than 4 bits to hex, replace{4}
with{1,4}
. However, converting back the result to binary, will produce a string that differs from the original. For example, converting forth and back"111101"
would produce"11110001"
. - In
hex2bin
, binary values are left-padded with zeroes so as to have 4 binary digits for every hex digit.
- 在 中
bin2hex
,如果您还想将小于 4 位的尾随块转换为十六进制,请替换{4}
为{1,4}
. 但是,将结果转换回二进制会产生与原始字符串不同的字符串。例如,前后转换"111101"
将产生"11110001"
. - 在 中
hex2bin
,二进制值左填充零,以便每个十六进制数字有 4 个二进制数字。
回答by Lukas Tutkus
To convert bin to hex and reverse i use these functions:
要将 bin 转换为十六进制并反转,我使用以下函数:
function bintohex()
{
mybin = document.getElementById('bin').value;
z = -1; number = 0;
for(i = mybin.length; i > -1; i--)
{
//Every 1 in binary string is converted to decimal and added to number
if(mybin.charAt(i) == "1"){
number += Math.pow(2, z);
}
z+=1;
}
// Return is converting decimal to hexadecimal
document.getElementById('result').innerHTML = number.toString(16);
}
function hextobin()
{
mybin = "";
/// Converting to decimal value and geting ceil of decimal sqrt
myhex = document.getElementById('hex').value;
mydec = parseInt(myhex, 16);
i = Math.ceil( Math.sqrt(mydec) );
while(i >= 0)
{
if(Math.pow(2, i) <= mydec){
mydec = mydec-Math.pow(2, i);
mybin += "1";
}else if(mybin != "")
mybin = mybin + "0";
i = i-1;
}
document.getElementById('result').innerHTML = mybin;
}
Input binary: <input type = "text" id = "bin">
<button onclick = "bintohex()">Convert to Hex</button><br />
Input Hecadecimal: <input type = "text" id = "hex">
<button onclick = "hextobin()">Convert to Bin</button><br />
Results: <div id = "result"></div>
Don't forget to check your answer.
不要忘记检查你的答案。