整型转换为字符数组
Integer into char array
我需要将整数值转换为位层上的字符数组。假设int有4个字节,我需要把它分成4个长度为1字节的块作为char数组。
的例子:
int a = 22445;
// this is in binary 00000000 00000000 1010111 10101101
...
//and the result I expect
char b[4];
b[0] = 0; //first chunk
b[1] = 0; //second chunk
b[2] = 87; //third chunk - in binary 1010111
b[3] = 173; //fourth chunk - 10101101
我需要这个转换非常快,如果可能的话没有任何循环(一些技巧与位操作可能)。我们的目标是在一秒钟内完成数千次这样的转换。
我不确定我是否推荐这样做,但您可以#include
<stddef.h>
和<sys/types.h>
并写入:
*(u32_t *)b = htonl((u32_t)a);
(htonl
是为了确保整数在存储之前是大端序)
int a = 22445;
char *b = (char *)&a;
char b2 = *(b+2); // = 87
char b3 = *(b+3); // = 173
根据您希望负数的表示方式,您可以简单地转换为unsigned
,然后使用遮罩和移位:
unsigned char b[4];
unsigned ua = a;
b[0] = (ua >> 24) & 0xff;
b[1] = (ua >> 16) & 0xff;
b[2] = (ua >> 8) & 0xff
b[3] = ua & 0xff;
(由于C规则将负数转换为无符号,这将产生负数的两个补码表示,这几乎肯定是您想要的)。
要访问任何类型的二进制表示,可以将指针强制转换为char指针:
T x; // anything at all!
// In C++
unsigned char const * const p = reinterpret_cast<unsigned char const *>(&x);
/* In C */
unsigned char const * const p = (unsigned char const *)(&x);
// Example usage:
for (std::size_t i = 0; i != sizeof(T); ++i)
std::printf("Byte %u is 0x%02X.n", p[i]);
也就是说,您可以将p
视为指向数组unsigned char[sizeof(T)]
的第一个元素的指针。(在你的情况下,T = int
.)
我在这里使用unsigned char
,这样您在打印二进制值时就不会遇到任何符号扩展问题(例如,在我的示例中通过printf
)。如果要将数据写入文件,则可以使用char
。
你已经接受了一个答案,但我还是会给出我的答案,这可能更适合你(或相同…)下面是我的测试:
int a[3] = {22445, 13, 1208132};
for (int i = 0; i < 3; i++)
{
unsigned char * c = (unsigned char *)&a[i];
cout << (unsigned int)c[0] << endl;
cout << (unsigned int)c[1] << endl;
cout << (unsigned int)c[2] << endl;
cout << (unsigned int)c[3] << endl;
cout << "---" << endl;
}
…这对我很有效。我知道你请求的是一个字符数组,但这是等价的。对于第一种情况,您还要求c[0] == 0, c[1] == 0, c[2] == 87, c[3] == 173,这里顺序颠倒了。
基本上,你使用相同的值,你只是访问它不同。
你可能会问,为什么我没有使用htonl() ?既然性能是一个问题,我认为你最好不要使用它,因为调用一个函数来确保字节将按某种顺序排列,当它们在某些系统上已经可以按这种顺序排列时,当你可以修改你的代码以使用不同的顺序时,如果不是这样的话,它似乎是浪费(宝贵的?)周期。
因此,您可以在之前检查顺序,然后根据测试结果使用不同的循环(更多的代码,但提高了性能)。
同样,如果你不知道你的系统使用的是2字节还是4字节的int,你可以先检查一下,然后根据结果再次使用不同的循环。
的要点是:你将有更多的代码,但你不会浪费循环的关键区域,这是在循环内。
如果您仍然有性能问题,您可以展开循环(在循环中重复代码,并减少循环计数),因为这也将节省几个循环。
注意,使用c[0], c[1]等。就c++而言,等于*(c), *(c+1)。
typedef union{
byte intAsBytes[4];
int int32;
}U_INTtoBYTE;
- 指向指向字符数组的指针数组的指针
- 比较字符数组
- 如何使用Crypto++并为RSA返回可打印的字节/字符数组
- 使用无符号字符数组有效存储内存
- 按字符值访问int数组
- 错误:字符数组的初始值设定项太多
- 对字符数组中的元素执行逐位操作
- C++,在int数组中输入字符串或字符会输出0,而不是ascii或error
- C++ 无法在字符数组中使用 for 循环打印字母模式
- 如何在 C++ 中从文件中读取字符数组(带有一些空格)
- 移动二维数组中的字符
- C++ 传递二维字符数组
- 无法在 C++ 中输入字符数组
- C++ 带结构的数组字符
- 数组字符包含量超出预期
- 读取文件并添加到数组字符
- 如何在Qt中更改或替换数组字符
- 为什么编译器不在参数中传递数组字符 *arr[] 的大小?
- 井字棋数组字符错误
- 分割数组字符