当前位置:  开发笔记 > 编程语言 > 正文

什么是time_t typedef到底是什么?

如何解决《什么是time_ttypedef到底是什么?》经验,为你挑选了6个好方法。

我在linux框中搜索并看到它是typedef

typedef __time_t time_t;

但找不到__time_t定义.



1> William Bren..:

该time_t的维基百科文章文章揭示了一些这方面的光.底线是time_tC规范中不保证类型.

time_t数据类型是用于存储系统时间值所定义的ISO C库中的数据类型.这些值从标准time() 库函数返回.此类型是标准头中定义的typedef.ISO C将time_t定义为算术类型,但未指定任何特定类型,范围,分辨率或编码.还未指定应用于时间值的算术运算的含义.

符合Unix和POSIX标准的系统将该time_t类型实现为signed integer(通常为32或64位宽),表示自Unix时期开始以来的秒数:1970年1月1日的午夜UTC(不计算闰秒).有些系统正确处理负时间值,而有些则没有.使用32位time_t类型的系统容易受到2038年问题的影响.


@Heath:在特定系统上,同一个人创建操作系统和C库,可能会在磁盘数据结构中使用`time_t`.但是,由于文件系统经常被其他操作系统读取,因此基于这种依赖于实现的类型定义文件系统是愚蠢的.例如,可能在32位和64位系统上使用相同的文件系统,而`time_t`可能会改变大小.因此,需要更精确地定义文件系统("自1970年初以来,以UTC为单位给出秒数的32位有符号整数"),而不仅仅是"time_t".
但请注意,time_t值通常只存储在内存中,而不是存储在磁盘上.相反,time_t被转换为文本或其他可移植存储格式的便携式格式.这使得Y2038问题确实不成问题.
@MichałGórny:修正了,只要文章没有删除,你就可以随时查看历史记录,以便找到正确的版本.
-1; Wikipedia引用POSIX保证对“ time_t”进行签名的说法是错误的。http://pubs.opengroup.org/onlinepubs/9699919799/basedefs/sys_types.h.html规定各种事物必须是“有符号整数类型”或“无符号整数类型”,但对于“ time_t”,它仅表示*“应为整数类型” *。一个实现可以使“ time_t”无符号,并且仍然符合POSIX。

2> Quassnoi..:

[root]# cat time.c

#include 

int main(int argc, char** argv)
{
        time_t test;
        return 0;
}

[root]# gcc -E time.c | grep __time_t

typedef long int __time_t;

$INCDIR/bits/types.h通过以下方式定义:

# 131 "/usr/include/bits/types.h" 3 4
# 1 "/usr/include/bits/typesizes.h" 1 3 4
# 132 "/usr/include/bits/types.h" 2 3 4


干净的把戏!因此可以通过这种方式发现所有类型

3> Ciro Santill..:

标准

威廉·布伦德尔引用维基百科,但我更喜欢马的嘴巴.

C99 N1256标准草案 7.23.1/3"时间组成部分"说:

声明的类型是size_t(在7.17中描述)clock_t和time_t,它们是能够表示时间的算术类型

6.2.5/18"类型"说:

整数和浮点类型统称为算术类型.

POSIX 7 sys_types.h说:

[CX] time_t应为整数类型.

其中[CX]被定义为:

[CX]扩展到ISO C标准.

这是一个延伸,因为它提供了更强有力的保证:浮点数已经出局.

gcc one-liner

无需创建Quassnoi提到的文件:

echo | gcc -E -xc -include 'time.h' - | grep time_t

在Ubuntu 15.10 GCC 5.2上,前两行是:

typedef long int __time_t;
typedef __time_t time_t;

命令明细与一些引用来自man gcc:

-E:"在预处理阶段后停止;不要正确运行编译器."

-xc:指定C语言,因为输入来自没有文件扩展名的stdin.

-include file:"处理文件好像"#include"file""出现在主要源文件的第一行."

-:从标准输入输入



4> 小智..:

答案肯定是特定于实现的.要明确找到您的平台/编译器,只需在代码中的某处添加此输出:

printf ("sizeof time_t is: %d\n", sizeof(time_t));

如果答案是4(32位)并且您的数据要超过2038,那么您有25年的时间来迁移代码.

如果您将数据存储为字符串,那么您的数据就可以了,即使它很简单:

FILE *stream = [stream file pointer that you've opened correctly];
fprintf (stream, "%d\n", (int)time_t);

然后以同样的方式读回它(fread,fscanf等等到int中),你就有了你的纪元偏移时间..Net中存在类似的解决方法.我在Win和Linux系统之间传递64位纪元数字没有问题(通过通信渠道).这带来了字节排序问题,但这是另一个主题.

要回答paxdiablo的查询,我会说,它印有"19100",因为该计划是这样写的(我承认我这样做是在80年代我自己):

time_t now;
struct tm local_date_time;
now = time(NULL);
// convert, then copy internal object to our object
memcpy (&local_date_time, localtime(&now), sizeof(local_date_time));
printf ("Year is: 19%02d\n", local_date_time.tm_year);

printf语句打印固定字符串"Year is:19",后跟一个零填充字符串,其中包含"1900年以来的年份"(定义tm->tm_year).在2000年,这个值显然是100."%02d"垫有两个零,但如果长度超过两位则不截断.

正确的方法是(仅改为最后一行):

printf ("Year is: %d\n", local_date_time.tm_year + 1900);

新问题:这种想法的基本原理是什么?



5> Eclipse..:

在Visual Studio 2008下,__int64除非您定义,否则默认为a _USE_32BIT_TIME_T.你最好假装你不知道它的定义是什么,因为它可以(并且将会)从平台变为平台.


如果30年内发生的事件是"此备份到期",那么您现在可能遇到麻烦,而不是在2038年.将30年添加到今天的32位time_t,您将获得过去的日期.您的程序会查找要处理的事件,找到一个已过期的事件(100年!)并执行它.哎呀,没有更多的备份.
@Rob,呸,离开吧!我们将在2036年开始像无头鸡一样跑来跑去,就像我们为Y2K做的那样.我们中的一些人将从Y2k38顾问那里赚到一大笔钱,Leonard Nimoy将带来另一本关于我们应该如何去躲藏在森林里的热闹书籍......
这通常有效,但是如果你的程序是为了跟踪将在30年后发生的事情,那么你*没有*签名的32位time_t是非常重要的.
顺便说一句,我们只发现了一个Y2K错误,这是一个将日期列为19100年1月1日的网页.为读者练习为什么......

6> abcoep..:

time_tlong int64位机器上的类型,否则它是long long int.

您可以在这些头文件中验证这一点:

time.h:/usr/include
types.htypesizes.h:/usr/include/x86_64-linux-gnu/bits

(下面的陈述不是一个接一个.可以使用Ctrl + f搜索在resp.头文件中找到它们.)

1)在 time.h

typedef __time_t time_t;

2)在 types.h

# define __STD_TYPE     typedef  
__STD_TYPE __TIME_T_TYPE __time_t;  

3)在 typesizes.h

#define __TIME_T_TYPE       __SYSCALL_SLONG_TYPE  
#if defined __x86_64__ && defined __ILP32__  
# define __SYSCALL_SLONG_TYPE   __SQUAD_TYPE  
#else
# define __SYSCALL_SLONG_TYPE   __SLONGWORD_TYPE
#endif  

4)再次进入 types.h

#define __SLONGWORD_TYPE    long int
#if __WORDSIZE == 32
# define __SQUAD_TYPE       __quad_t
#elif __WORDSIZE == 64
# define __SQUAD_TYPE       long int  

#if __WORDSIZE == 64
typedef long int __quad_t;  
#else
__extension__ typedef long long int __quad_t;


到处都不是"长int".请参阅http://stackoverflow.com/questions/384502/what-is-the-bit-size-of-long-on-64-bit-windows
推荐阅读
贾志军
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有