我收到一个128位的二进制地址,我需要将其转换为十六进制格式。这就是我要做的事情:
我需要将它分成8个16位的块,所以我将有8个变量,每个变量都有16位。
0010000111011010 0000000011010011 0000000000000000 0010111100111011 0000001010101010 0000000011111111 0000000000000000 0000000000000000
现在,我需要进一步将这些16位分成4位,即每个半字节
0010 0001 1101 1010
0000 0000 1101 0011
0000 0000 0000 0000
所以,现在我将为每个变量获得四个子变量
然后,我需要将每个子变量转换为十六进制
0010 0001 1101 1010
2 1 D A
合并所有子变量并以十六进制格式形成IPv6地址:
21DA:00D3:0000:2F3B:02AA:00FF:0000:0000
有谁能告诉我如何用C ++做到这一点?
答案 0 :(得分:3)
要获得16位值的四个最高位,请将其右移12位。这将导致顶部位为零,因此不需要屏蔽。对于其他人,您(可选)向右移动并使用按位和运算符&
屏蔽四个最低位。
要将从上述步骤获得的值转换为字符形式的十六进制数字,那么对于低于10的值,添加'0'
(如果您使用的是带有ASCII编码的计算机),以及10或更高然后减去10并添加例如'A'
。
当然有更简单的方法,例如使用例如sprintf
直接转换数字。只需将16位值转换为无符号短整数即可,例如。
printf("%04hx\n", value_as_unsigned_short);
假设你有二进制数0001001010101011
。这是十六进制表示12ab
。
如果二进制数是一个整数变量,让我们说一个名为value
的变量,我们可以将十六进制表示形式化为这样的字符串:
// First get each digit, one by one
digit0 = value & 0x0f; // Mask out everything but the lowest four bits
digit1 = (value >> 4) 0x0f;
digit2 = (value >> 8) 0x0f;
digit3 = value >> 12;
// Now make a string out of those four digits
char str[5]; // Four digits plus the string terminator
// If a digit is less than 10, then add '0' to get an ASCII character
// Else decrease by ten (to get a number between 0 and 5) and add 'A'
str[0] = digit3 < 10 ? digit3 + '0' : (digit3 - 10) + 'A';
str[1] = digit2 < 10 ? digit2 + '0' : (digit2 - 10) + 'A';
str[2] = digit1 < 10 ? digit1 + '0' : (digit1 - 10) + 'A';
str[3] = digit0 < 10 ? digit0 + '0' : (digit0 - 10) + 'A';
str[4] = '\0'; // Terminate string
printf("value is in hex %s\n", str);
上面的代码将打印
value is in hex 12AB
然而,这是很多代码,尽管它可以重复用于所有数字。如果你已经在整数变量value
中有了16位数字,那么就可以更容易地编写
printf("value is in hex %04hX\n", value);
上面两个代码段的结果都是一样的。
关于你的编辑:
std::ostringstream oss;
for (size_t i = 0; i < 8; ++i, aBinaryIPAddress += 2)
{
// Take the first byte, and shift it left 8 bits, making it
// the high byte of a 16-bit number. Then or (or add) the next
// byte at the low 8 bits in the 16-bit number.
// The casting is needed because we're working with 16-bit numbers
// and not bytes.
uint16_t value = static_cast<uint16_t>(*aBinaryIPAddress << 8) |
static_cast<uint16_t>(*(aBinaryIPAddress + 1));
oss << std::setfill('0') << std::setw(4) << std::hex << value;
if (i < 7)
oss << ':';
}
std::cout << "Address is " << oss.str() << '\n';
答案 1 :(得分:2)
您可以使用sprintf和格式说明符X将整数值打印为十六进制。无需将每个块分成4个字节以上。所以如果你有这个:
string a = "00100001110110100000000011010011";
unsigned value = 0;
for (int i = 0;i < a.size();++i) {
value = value * 2 + a[i] - '0';
}
printf("%04X\n", value);
将解决您问题的很大一部分。我上面使用了printf来演示stdout上的输出。