世界时、UTC、GPS时、本地时间、闰秒
2010-05-10 08:26阅读:
(一)时间系统
世界时是基于地球自转的一种时间计量系统,反映了地球在空间的位置。
原子时是基于原子物理技术的一种更加均匀的时间系统,对于测量时间间隔非常重要。
由于两种时间尺度速率上的差异,一般来说1~2年会差1秒。
协调世界时(UTC , Universal Time
Coordinated)是我们日常生活所用的时间,是一种折衷的时间尺度,它用原子时的速率,而在时刻上逼近世界时,所用方法就是“闰秒”,当协调世界时和世界时之差即将超过±0.9秒时,就对协调世界时作一整秒的调整。UTC在本质上还是一种原子时,因为它的秒长规定和原子时秒长相等,只是在时刻上,通过人工干预(闰秒),尽量靠近世界时。方法是:必要时对协调世界时作一整秒的调整(增加1秒或去掉1秒),使UTC和世界时的时刻之差保持在±0.9秒以内。这一技术措施就称为闰秒(或跳秒),增加1秒称为正闰秒(或正跳秒);去掉1秒称为负闰秒(或负跳秒)。是否闰秒,由国际地球自转服务组织(IERS)决定。闰秒的首选日期是每年的12月31日和6月30日,或者是3月31日和9月30日。如果是正闰秒,则在闰秒当天的23时59分59秒后插入1秒,插入后的时序是:…58秒,59秒,60秒,0秒,…,这表示地球自转慢了,这一天不是86400秒,而是86401秒;如果是负闰秒,则把闰秒当天23时59分中的第59秒去掉,去掉后的时序是:…57秒,58秒,0秒,…,这一天是86399秒。
最近的一次闰秒是在2005年底实施的。2005年7月4日,国际地球自转服务组织(IERS)发布C公报,协调世界时(UTC)将在2005年底实施一个正闰秒,即增加1秒。届时,所有的时钟将拨慢1秒。具体实施步骤如下:
UTC协调世界时:
23时59分59秒(2005年12月31日)
23时59分60秒(2005年12月31日)
00时00分00秒(2006年1月1日)
相应地,北京时间:
7时59分59秒(2006
年1月1日)
7时59分60秒(2006年1月1日)
8时00分00秒(2006年1月1日)
之前的一次闰秒发生在1999年1月1日。国家授时中心(陕西天文台)在1998年11月的《时间频率公报》中提前数月向全国时间用户通知了这一消息,使BPM、BPL时号用户周知。
历年UTC跳秒情况见附表一。
跳秒始于1972年1月1日,在此之前UTC相对于TA的调整调整采用调偏频率的方法,调整情况见附表二。
值得注意的是原子时与世界时分别来自于两个互不相干的系统,虽然协调时基本上解决了两者之间的协调问题,但是由于地球自转速度越来越慢加之不均匀,闰秒时间间隔也不均匀。
(二)时间转换
本地时间 = UTC+时区差
(北京时间 = UTC+8)
GPS时间与UTC时间差了一个闰秒。闰秒数在下行的导航电文中有反应。GPGGA和GPRMC中本身已经将GPS时间转换为UTC时间了。
北京时间=GPS时+8小时-闰秒。
(三)UTC时间转换为北京时间的转换程序(2000年以后)
输入参数:年(2位),月,日,时,分,秒
void Calc( int y, int m, int d, int hh, int mm, int ss )
{
int w;
// 星期
hh += 8;
// 格林威治时间 + 8 小时 = 北京时间
if( hh < 24 )
goto l_out;
// 没有跨天,则计算完成
///////////// 下面是跨天后的计算
/////////////////////////////
hh -= 24;
d ++;
// 日期加一天
switch( m )
// 按月判断
{
case 4:
case 6:
// 跨小月的判断
case 9:
case 11:
if( d >
30 ) {
d = 1;
m ++;
}
break;
case 1:
case 3:
// 跨大月的判断
case 5:
case 7:
case 8:
case 10:
if( d >
31 ) {
d = 1;
m ++;
}
break;
case 12:
// 12 月,要判断是否跨年
if( d >
31 ) {
y ++;
d = 1;
m = 1;
}
break;
case 2:
// 2
月,要判断是否是闰年
if( (
(y+2000)%400 == 0 ) ||
// 能被400整除,一定是闰年
( (y+2000)%4 ==0 ) && (
(y+2000)%100 !=0 ) )
//
能被4整除,但不能被100整除,一定是闰年
{
if( d>29 )
//
闰年2月,可以有29号
{
m = 3;
d = 1;
}
}
else if(
d>28 )
// 非闰年2月,可以有28号
{
m = 3; d = 1;
}
break;
}
l_out:
// 计算完成,开始输出
printf( '%04d.%02d.%02d - %02d:%02d:%02d',
y+2000, m, d, hh, mm, ss);
if( 1 == m ) {
y --;
m =
13;
}
else if( 2 == m ) {
y --;
m =
14;
}
w = y + y/4 + 26 * ( m + 1 ) / 10 + d -
1;
w %= 7;
// 0 表示星期日
printf ( ' week=%d ', w );
}
附表一
UTC历年跳秒一览表
日 期
|
跳秒(秒)
|
UTC -TA(秒)
|
1972.1.1
|
-0.1077580
|
-10
|
1972.7.1
|
-1
|
-11
|
1973.1.1
|
-1
|
-12
|
1974.1.1
|
-1
|
-13
|
1975.1.1
|
-1
|
-14
|
1976.1.1
|
-1
|
-15
|
1977.1.1
|
-1
|
-16
|
1978.1.1
|
-1
|
-17
|
1979.1.1
|
-1
|
-18
|
1980.1.1
|
-1
|
-19
|
1981.7.1
|
-1
|
-20
|
1982.7.1
|
-1
|
-21
|
1983.7.1
|
-1
|
-22
|
1985.7.1
|
-1
|
-23
|
1988.1.1
|
-1
|
-24
|
1990.1.1
|
-1
|
-25
|
1991.1.1
|
-1
|
-26
|
1992.7.1
|
-1
|
-27
|
1993.7.1
|
-1
|
-28
|
1994.7.1
|
-1
|
-29
|
1996.1.1
|
-1
|
-30
|
1997.7.1
|
-1
|
-31
|
1999.1.1
|
-1
|
-32
|
2000.1.1
|
0
|
-32
|
2001.1.1
|
0
|
-32
|
附表二
UTC相对于TA的调整(UTC-TA)一览表
年份
|
频率调偏
|
时刻阶跃
|
1960
|
-150×10-10
|
|
1961
|
-150×10-10
|
8月1日0hUT,+50ms
|
1962
|
-130×10-10
|
|
1963
|
-130×10-10
|
11月1日0hUT,-100ms
|
1964
|
-150×10-10
|
4月1日,9月1日0hUT,各-100ms
|
1965
|
-150×10-10
|
1月1日, 7月1日,9月1日0hUT,各-100ms
|
1966
|
-300×10-10
|
|
1967
|
-300×10-10
|
|
1968
|
-300×10-10
|
2月1日0hUT,+100ms
|
1969
|
-300×10-10
|
|
1970
|
-300×10-10
|
|
1971
|
-300×10-10
|
|
1972
|
0
|
1月1日0hUT,-107.758ms,7月1日-1000ms
|