Dan*_*ant 17
好吧,你可以将它全部打包成一个unsigned short(那是2个字节,5个位表示Day,5位表示小时,6位表示分钟)...并使用一些移位和屏蔽来获取值.
unsigned short timestamp = <some value>; // Bits: DDDDDHHHHHMMMMMM
int day = (timestamp >> 11) & 0x1F;
int hour = (timestamp >> 6) & 0x1F;
int min = (timestamp) & 0x3F;
unsigned short dup_timestamp = (short)((day << 11) | (hour << 6) | min);
Run Code Online (Sandbox Code Playgroud)
或使用宏
#define DAY(x) (((x) >> 11) & 0x1F)
#define HOUR(x) (((x) >> 6) & 0x1F)
#define MINUTE(x) ((x) & 0x3F)
#define TIMESTAMP(d, h, m) ((((d) & 0x1F) << 11) | (((h) & 0x1F) << 6) | ((m) & 0x3F)
Run Code Online (Sandbox Code Playgroud)
(你在当前版本的问题中没有提到月/年,所以我省略了它们).
[ 编辑:使用unsigned short- 未签名short.]
你的意思是0-23和分钟0-59?我听说过闰秒但不是闰秒或小时.
(log (* 31 60 24) 2)
=> 15.446
Run Code Online (Sandbox Code Playgroud)
因此,您可以将这些值拟合为16位或2个字节.这是一个好主意是一个完全不同的问题.
您可以使用位域并使用编译器/平台特定的pragma来保持紧密:
typedef struct packed_time_t {
unsigned int month : 4;
unsigned int date : 5;
unsigned int hour : 5;
unsigned int minute : 6;
} packed_time_t;
Run Code Online (Sandbox Code Playgroud)
但你真的需要这个吗?标准时间功能不足够吗?位域根据架构,填充等而有所不同......不是便携式构造.
为什么不直接使用 Ctime()函数的(4 字节?)输出NULL作为参数。这只是 Unix 纪元时间(即自 1970 年 1 月 1 日以来的秒数)。就像乔的回答一样,它为您提供了比任何试图将数月、数天和数年打包成小块的答案更大的成长空间。这是标准的。time_t在标准 C(至少在 Unix 上)中,将变量转换为实际时间是微不足道的,并且大多数情况下,如果您有一个打算保存 3 字节变量的数据结构,则无论如何它都可能被四舍五入为 4 字节。
我知道您正在尝试针对大小进行大量优化,但是 4 个字节实在是太小了。即使您截断了最高字节,您仍然可以从中获得 194 天的不同时间。
您可以time(NULL)通过在存储之前花费时间并将其除以 60,将其截断为一分钟并存储它来获得更多收益。如上所示,其中 3 个字节为您提供 388 个月,2 个字节您可以存储 45 天。
我会选择 4 字节版本,仅仅是因为我不认为 2、3 和 4 字节之间的区别对于任何正在运行的程序是否重要或至关重要(除非它是引导加载程序)。它更容易获得和处理,并且最终可能会为您省去很多麻烦。
编辑:我发布的代码不起作用。我已经睡了 3 个小时,最终我会弄清楚如何正确地进行处理。在此之前,您可以自己实现这一点。