iOS关于时间的处理

最近碰到了一些关于时间的问题, 网上搜了一下后得到了很多时间处理的方法,在此和大家分享一下
首先了解一下两个标准时间

1.GMT和UTC

1.1 GMT

格林尼治标准时间 (Greenwich Mean Time,GMT)是指位于英国伦敦郊区的皇家格林尼治天文台当地的标准时间,因为本初子午线被定义为通过那里的经线。
自1924年2月5日开始,格林尼治天文台负责每隔一小时向全世界发放调时信息。
理论上来说,格林尼治标准时间的正午是指当太阳横穿格林尼治子午线时(也就是在格林尼治上空最高点时)的时间。但由于地球在它的椭圆轨道里的运动速度不均匀,这个时刻可能与实际的太阳时有误差,最大误差达16分钟。原因在于地球每天的自转是有些不规则的,而且正在缓慢减速,因此格林尼治时间基于天文观测本身的缺陷,已经不再被作为标准时间使用。现在的标准时间,是由原子钟报时的协调世界时(UTC)来决定。

1.2 UTC

协调世界时, 又称世界标准时间或世界协调时间,简称UTC(Coordinated Universal Time)是最主要的世界时间标准,其以原子时秒长为基础,在时刻上尽量接近于格林尼治标准时间。
协调世界时是世界上调节时钟和时间的主要时间标准,它与0度经线的平太阳时相差不超过1秒[1],并不遵守夏令时。协调世界时是最接近格林威治标准时间(GMT)的几个替代时间系统之一。对于大多数用途来说,UTC时间被认为能与GMT时间互换,但GMT时间已不再被科学界所确定。
如果本地时间比UTC时间快,例如中国大陆[a]、香港、澳门、台湾、蒙古国、新加坡、马来西亚、澳大利亚西部的时间比UTC快8小时,就会写作UTC+8,俗称东8区。相反,如果本地时间比UTC时间慢,例如夏威夷的时间比UTC时间慢10小时,就会写作UTC-10,俗称西10区。
以上是我从维基百科摘选下来的部分解释.可以了解一下


2.NSDate

2.1 NSDate使用方法

NSDate *date = [NSDate date];
NSLog(@"%@",currentDate);
NSLog(@“current date interval: %f”, [date timeIntervalSinceReferenceDate]);

输出后的结果:

2017-06-21 16:21:34.577 Time[44723:2002871] 2017-06-21 08:21:34 +0000
2017-06-21 16:21:34.578 Time[44723:2002871] current date interval: 519726094.576822

timeIntervalSinceReferenceDate返回的是距离参考时间的偏移量,这个偏移量的值为519726094秒,502945767/86400/365=15.9483056506,86400是一天所包含的秒数,365大致是一年的天数,15.94当然就是年数了,算出来刚好是此刻距离2001年的差值。

北京时间为UTC+8小时,所以当我们使用NSDate打印出当前的时间戳的时候,是当前的时间减去8小时.
并且NSDate受系统时间控制的,也就是说,当你修改了手机上的时间显示,NSDate获取当前时间的输出也会随之改变。在我们做App的时候,明白这一点,就知道NSDate并不可靠,因为用户可能会修改它的值。

2.2 转换格式

NSDateFormatter *dateFormatter = [[NSDateFormatter alloc]init];
[dateFormatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
NSString *dateStr = [dateFormatter stringFromDate:date];
NSLog(@"字符串表示:%@",dateStr);

打印输出:
2017-06-21 16:45:54.405 Time[45415:2026413] 字符串表示:2017-06-21 16:45:54

2.3 获取北京时间,获取昨天此刻,获取明天此刻,昨天和今天的时间差 (NSDate -> NSDate)

//1.获取当前时间 零时区的时间
    NSDate *date = [NSDate date];
    NSLog(@"当前零时区时间 %@", date);

    //2.获得本地时间 东八区 晚八个小时 以秒计时
    NSDate *date1 = [NSDate dateWithTimeIntervalSinceNow:8 * 60 * 60];
    NSLog(@"今天此时的时间 %@",date1);

    //3.昨天此时的时间
    NSDate *yesterdayDate = [NSDate dateWithTimeIntervalSinceNow:(-24 + 8) * 60 * 60];
    NSLog(@"昨天此时的时间 %@",yesterdayDate);

    //4.明天此刻
    NSDate *tomorrowDate = [NSDate dateWithTimeInterval:24 * 60 * 60 sinceDate:date1];
    NSLog(@"明天此刻的时间 %@",tomorrowDate);

    //5.NSTimeInterval 时间间隔(单位:秒)
    //昨天此时与明天此刻的时间间隔
    NSTimeInterval timeInterval = [tomorrowDate timeIntervalSinceDate:yesterdayDate];
    NSLog(@"昨日和明天此刻的时间(秒) %.0f",timeInterval);

打印输出的结果:

当前零时区时间 2017-06-21 08:59:40 +0000
今天此时的时间 2017-06-21 16:59:40 +0000
昨天此时的时间 2017-06-20 16:59:40 +0000
昨天此时的时间 2017-06-20 16:59:40 +0000
昨日和明天此刻的时间(秒) 172800

苹果官方文档关于NSDate的解释

3.gettimeofday

这个API也能返回一个描述当前时间的值

struct timeval time;
gettimeofday(&time,nil);
NSLog(@"gettimeofday: %ld,%d”,time.tv_sec,time.tv_usec);

使用gettimeofday获得的值是Unix Time
Unix Time: 是以UTC 1970年1月1号 00:00:00为基准时间,当前时间距离基准点偏移的秒数。上述API返回的值是1498036308,表示当前时间距离UTC 1970年1月1号 00:00:00一共过了1498036308秒。

实际上NSDate也有一个API能返回Unix time:
NSDate* date = [NSDate date];
NSLog(@”timeIntervalSince1970: %f”, [date timeIntervalSince1970]);

gettimeofday和NSDate,CFAbsoluteTimeGetCurrent()一样,都是受当前设备的系统时间影响。只不过是参考的时间基准点不一样而已。我们和服务器通讯的时候一般使用Unix time。


4.mach_absolute_time()

mach_absolute_time()可能用到的时候比较少,但这个概念非常重要。
前面提到我们需要找到一个均匀变化的属性值来描述时间,而在我们的iPhone上刚好有一个这样的值存在,就是CPU的时钟周期数(ticks)。这个tick的数值可以用来描述时间,而mach_absolute_time()返回的就是CPU已经运行的tick的数量。将这个tick数经过一定的转换就可以变成秒数,或者纳秒数,这样就和时间直接关联了。
不过这个tick数,在每次手机重启之后,会重新开始计数,而且iPhone锁屏进入休眠之后tick也会暂停计数。
mach_absolute_time()不会受系统时间影响,只受设备重启和休眠行为影响。


5.CACurrentMediaTime()

官方文档定义:

/* Returns the current CoreAnimation absolute time. This is the result of
 * calling mach_absolute_time () and converting the units to seconds. */
CFTimeInterval CACurrentMediaTime (void)

CACurrentMediaTime()就是将上面mach_absolute_time()的CPU tick数转化成秒数的结果。以下代码

double mediaTime = CACurrentMediaTime();
NSLog(@"CACurrentMediaTime: %f", mediaTime);

返回的就是开机后设备一共运行了(设备休眠不统计在内)多少秒,另一个API也能返回相同的值:

NSTimeInterval systemUptime = [[NSProcessInfo processInfo] systemUptime];
NSLog(@"systemUptime: %f", systemUptime);

打印输出:

2017-06-21 17:23:14.682 NSDate博客Demo[46674:2065572] CACurrentMediaTime: 203416.680109
2017-06-21 17:23:14.682 NSDate博客Demo[46674:2065572] systemUptime: 203416.680286

CACurrentMediaTime()也不会受系统时间影响,只受设备重启和休眠行为影响。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值