由于Mac OS X不支持获取时间,我发现这个要点以便携式方式使用clock_gettime基金:
void current_utc_time(struct timespec *ts) {
#ifdef __MACH__ // OS X does not have clock_gettime, use clock_get_time
clock_serv_t cclock;
mach_timespec_t mts;
host_get_clock_service(mach_host_self(), CALENDAR_CLOCK, &cclock);
clock_get_time(cclock, &mts);
mach_port_deallocate(mach_task_self(), cclock);
ts->tv_sec = mts.tv_sec;
ts->tv_nsec = mts.tv_nsec;
#else
clock_gettime(CLOCK_REALTIME, ts);
#endif
}
像这样使用它
struct timespec requestStart;
current_utc_time(&requestStart);
printf("start: s: %lu\n", requestStart.tv_sec);
printf("start: ns: %lu\n", requestStart.tv_nsec);
start: s: 1435988139
start: ns: 202015000
我试图从这段代码中获取秒和毫秒值,这是从纳秒值获得毫秒的正确方法吗?
printf("total: ms: %lu\n", (requestStart.tv_nsec - requestEnd.tv_nsec) / (unsigned long)1000000);
如果是这样,我如何获得秒值?如果不是,我怎么能得到毫秒和秒值?
修改 在回应第一条评论时,我主要是寻找一种让代码尽可能便携的方法。
答案 0 :(得分:2)
如果您想要便携性,只需使用gettimeofday
即可。这应该适用于所有地方clock_gettime
似乎是 Linux特定的是一个相对较新的Posix介绍。
转换时:struct timeval
(由gettimeofday
和其他旧函数使用)使用微秒。较新的struct timespec
使用纳秒。所以要来回转换,你会乘以或除以1000。
计算差异时,你必须担心进位/溢出,所以表达
(requestStart.tv_nsec - requestEnd.tv_nsec) / (unsigned long)1000000
是不正确的,原因有两个:差异可能是负面的(也就是说,如果时间从123.456变为124.321),并且你将它缩小太多。
当我计时某些操作时,我通常会这样做:
struct timeval before, after, elapsed;
gettimeofday(&before, NULL);
sleep(1);
gettimeofday(&after, NULL);
elapsed.tv_sec = after.tv_sec - before.tv_sec;
if(after.tv_usec >= before.tv_usec)
elapsed.tv_usec = after.tv_usec - before.tv_usec;
else {
elapsed.tv_sec--;
elapsed.tv_usec = 1000000 + after.tv_usec - before.tv_usec;
}
printf("elapsed: %d.%06ld\n", (int)elapsed.tv_sec, (long)elapsed.tv_usec);
如果我想要struct timespec
(使用纳秒),我会乘以1000:
struct timespec elapsed2;
elapsed2.tv_sec = elapsed.tv_sec;
elapsed2.tv_nsec = elapsed.tv_usec * 1000;
printf("elapsed: %d.%09ld\n", (int)elapsed2.tv_sec, (long)elapsed2.tv_nsec);
要从struct timespec
转换回struct timeval
,我除以1000:
struct timeval elapsed3;
elapsed3.tv_sec = elapsed2.tv_sec;
elapsed3.tv_usec = elapsed2.tv_nsec / 1000;
另一个有用的东西是将秒和子秒作为浮点:
double e = (double)elapsed.tv_sec + elapsed.tv_usec / 1e6;
double e2 = (double)elapsed2.tv_sec + elapsed2.tv_nsec / 1e9;
printf("float: %f %f\n", e, e2);
(事实证明,编写此类代码时可能存在细微差别,具体取决于tv_sec
和tv_usec
或tv_nsec
的实际类型,以及"您的编译器可能会选择给您提供帮助"警告。请参阅this question。)
答案 1 :(得分:0)
#import <time.h>
#import <sys/timeb.h>
struct timeb timebCurrentTime;
ftime(&timebCurrentTime);
double y = (double)timebCurrentTime.time + (double)timebCurrentTime.millitm / 1000;//current time in sec since 1970-01-01 00:00:00 +0000 (UTC)