我有一个无符号的字符数组,其尺寸是6字节数组的内容是一个整数(因为UNIX时间的秒4096 *号)。我知道字节数组是big-endian。如何将48位字节数组转换为C中的64位整数?
有没有在C库函数,我可以使用该字节数组转换成int_64还是我不得不手动做呢?
谢谢!
PS:万一你需要更多的信息,是的,我试图解析Unix时间戳。 Here是我处理的时间戳的格式规范。
我有一个无符号的字符数组,其尺寸是6字节数组的内容是一个整数(因为UNIX时间的秒4096 *号)。我知道字节数组是big-endian。如何将48位字节数组转换为C中的64位整数?
有没有在C库函数,我可以使用该字节数组转换成int_64还是我不得不手动做呢?
谢谢!
PS:万一你需要更多的信息,是的,我试图解析Unix时间戳。 Here是我处理的时间戳的格式规范。
C99的实现可以提供uint64_t
(它没有提供它,如果没有本地固定宽度的整数,这正是64位),在这种情况下,你可以使用:
#include <stdint.h>
unsigned char data[6] = { /* bytes from somewhere */ };
uint64_t result = ((uint64_t)data[0] << 40) |
((uint64_t)data[1] << 32) |
((uint64_t)data[2] << 24) |
((uint64_t)data[3] << 16) |
((uint64_t)data[4] << 8) |
((uint64_t)data[5] << 0);
如果您的C99实现不提供uint64_t
你仍然可以使用unsigned long long
或(我认为)uint_least64_t
。无论主机的本地排序如何,这都可以工作。
你有没有试过这样:
unsigned char a [] = {0xaa,0xbb,0xcc,0xdd,0xee,0xff};
unsigned long long b = 0;
memcpy(&b,a,sizeof(a)*sizeof(char));
cout << hex << b << endl;
或者你可以用手,这将避免一些建筑的具体问题做。
我建议使用正常整数运算(总和和移位),而不是试图模仿存储器块排序,其不大于在兼容性的术语上述方案更好。
仅当字节序与本地字节序匹配时才有效。 –
是的。预处理器条件可能有助于选择正确的方式(如果性能很关键)。 –
Nooooo no no no。请参阅弗朗西斯科·索托的答案中的博客文章,了解为什么在这些情况下应避免预处理器条件。 – dreamlax
可以使用取决于编译器
#pragma pack(1)
或
__attribute__((packed))
组选
typedef struct __uint48_t uint48_t;
struct __attribute__((packed)) __uint48_t {
uint64_t _m:48;
};
__uint48_t data;
uint64_t result = data._m;
我想做到这一点的最好办法是使用一个工会。
union time_u{
uint8_t data[6];
uint64_t timestamp;
}
然后你可以使用的内存空间作为一个字节数组或uint64_t中,通过引用
union time_u var_name;
var_name.data[i]
var_name.timestamp
您必须手动这是很容易做到这一点。既然你是用字节顺序涉足,我建议你阅读[这](http://commandcenter.blogspot.com/2012/04/byte-order-fallacy.html)罗布·派克的博客文章了。文章中包含了对你有所帮助的代码,只是不要直视它,阅读它。 –
没有标准的C函数来做到这一点。不过,有可能是由使用此格式的任何库提供的函数。 –