第二章 坐标系与时间系统:常用坐标系定义、时间系统转换
各位同学,咱们今天聊聊入轨段制导设计里最基础、也最容易栽跟头的两个东西——坐标系和时间系统。
说实话,我见过不少年轻工程师,算法写得漂亮,仿真跑得飞起,结果一到实际任务就出问题。查到最后,十有八九是坐标系搞混了,或者时间基准没对齐。嗯,这玩意儿看着简单,但坑是真的多。
2.1 常用坐标系定义
先说说坐标系。你想想看,航天器在天上飞,你得知道它“在哪儿”、“朝哪儿飞”、“姿态怎么样”。这些信息,都得靠坐标系来描述。
我个人习惯把坐标系分成三类:惯性系、地固系、本体系。咱们一个一个来。
2.1.1 地心惯性坐标系(ECI)
这个坐标系,说白了就是“不动”的参考基准。它的原点在地心,X轴指向春分点,Z轴指向地球自转轴(北极方向),Y轴按右手定则补齐。
为什么需要它?因为牛顿定律只适用于惯性系。你算轨道、推积分,都得在ECI里做。我在项目中遇到过有人直接在ECEF里算轨道递推,结果偏差越来越大,查了半天才发现是坐标系没转回去。
关键点:ECI是“静止”的,ECEF是“跟着地球转”的。两者之间差一个地球自转角度。
2.1.2 地心地固坐标系(ECEF)
ECEF的原点也在球心,但它的X轴指向本初子午线与赤道的交点,Z轴还是北极,Y轴补齐。这个坐标系跟着地球一起转。
你平时看到的经纬高(LLA),就是从ECEF换算过来的。地面站测控、GPS定位,用的都是ECEF。我记得有一次做星箭分离分析,箭上给的分离参数是ECI下的,星上却用ECEF算相对位置,结果差了将近7公里——还好是在仿真阶段发现的。
避坑指南:我曾经在接口文档里看到“位置矢量”四个字,没写坐标系。结果两个团队各用各的,联调时对不上。从此以后,我要求所有接口必须显式标注坐标系类型。
2.1.3 轨道坐标系(LVLH)
这个坐标系跟着航天器走。原点在航天器质心,X轴沿速度方向(V-bar),Z轴指向地心(R-bar),Y轴按右手定则(H-bar,即轨道角动量方向)。
做交会对接、编队飞行的时候,LVLH特别好用。你想啊,相对位置用“前、上、右”来描述,比用ECI里的XYZ直观多了。
2.1.4 本体坐标系(Body Frame)
本体系固连在航天器上。原点在质心,X轴通常指向飞行方向(或对地方向),Y、Z轴按任务需求定义。
姿态控制、推力方向计算,都在本体系里做。你想想看,发动机装在星体上,推力方向当然用本体系描述最方便。
| 坐标系 | 原点 | 特点 | 典型用途 |
|---|---|---|---|
| ECI | 地心 | 惯性、不旋转 | 轨道积分、动力学 |
| ECEF | 地心 | 随地球旋转 | 地面站、GPS |
| LVLH | 航天器质心 | 随轨道运动 | 交会对接、编队 |
| Body | 航天器质心 | 固连星体 | 姿态控制、推力 |
2.2 坐标系转换
坐标系之间怎么转?核心就是旋转矩阵。ECI到ECEF,绕Z轴转一个格林尼治恒星时角(GAST)。ECI到LVLH,先转到轨道系,再转到LVLH。
我给大家一个常用的ECI→ECEF转换代码片段,C语言风格:
/* ECI to ECEF 转换 */
/* 输入:r_eci[3], 时间t(儒略日) */
/* 输出:r_ecef[3] */
double gmst = calc_gmst(t); // 计算格林尼治恒星时
double cos_g = cos(gmst);
double sin_g = sin(gmst);
r_ecef[0] = cos_g * r_eci[0] + sin_g * r_eci[1];
r_ecef[1] = -sin_g * r_eci[0] + cos_g * r_eci[1];
r_ecef[2] = r_eci[2]; // Z轴不变
小技巧:我习惯把所有旋转矩阵写成函数,统一管理。这样代码可读性好,也不容易出错。另外,记得检查旋转矩阵的行列式是不是1——如果不是,说明你写错了。
2.3 时间系统
时间系统比坐标系还容易乱。为什么?因为有好几种“时间”,各有各的用处。
2.3.1 世界时(UT1)
UT1基于地球自转。说白了,就是“太阳走到头顶了,那就是中午12点”。但地球自转不均匀,所以UT1也不是均匀的。
2.3.2 国际原子时(TAI)
TAI基于原子钟,均匀、稳定。从1958年1月1日开始累积。你想想看,原子钟几百万年才差一秒,比地球靠谱多了。
2.3.3 协调世界时(UTC)
UTC是折中方案。它用TAI的秒长,但通过“闰秒”来和UT1对齐。目前UTC比TAI慢了37秒(这个数字会变)。
我记得有一次做任务规划,地面站给的过境时间是UTC,星上用的却是TAI。结果差了37秒,整个测控弧段全对不上。嗯,从那以后我养成了一个习惯——所有时间接口必须标注时间系统。
2.3.4 儒略日(JD)与简化儒略日(MJD)
儒略日是一个连续计数的时间系统。从公元前4713年1月1日开始,每天加1。MJD = JD - 2400000.5,数值小一些,方便计算。
做轨道计算的时候,我几乎只用MJD。因为数值小,精度损失也小。
| 时间系统 | 基准 | 特点 | 典型用途 |
|---|---|---|---|
| UT1 | 地球自转 | 不均匀 | 天文观测 |
| TAI | 原子钟 | 均匀、稳定 | 科学计算 |
| UTC | TAI+闰秒 | 民用标准 | 地面测控 |
| MJD | 连续计数 | 数值小、方便 | 轨道计算 |
2.4 时间系统转换
UTC转TAI:加上闰秒数。TAI转UT1:查地球自转参数(EOP)。这些转换都有标准算法,IERS(国际地球自转服务)每年都会发布数据。
我给大家一个UTC→MJD的转换函数:
/* UTC 转 MJD */
/* 输入:year, month, day, hour, min, sec */
/* 输出:MJD */
double utc_to_mjd(int y, int m, int d, int h, int min, double s) {
// 先转JD,再减2400000.5
double jd = 367*y - floor(7*(y+floor((m+9)/12))/4)
+ floor(275*m/9) + d + 1721013.5
+ (h + min/60.0 + s/3600.0) / 24.0;
return jd - 2400000.5;
}
注意:闰秒是每年6月30日或12月31日加(或减)的。我建议你写代码时不要硬编码闰秒数,而是从IERS的EOP文件里读取。否则每年都得改代码,容易漏。
2.5 知识体系总览
下面这张图,是我自己总结的坐标系与时间系统知识框架。你把它记住了,后面学制导律会轻松很多。
好了,这一章的内容就这些。坐标系和时间系统是制导律设计的“地基”,地基不稳,上面盖什么都白搭。你回去之后,把ECI和ECEF的转换手推一遍,再把UTC和MJD的转换代码写一写。下次咱们聊入轨段制导的动力学模型——那才是真正有意思的东西。
公众号:蓝海资料掘金营,微信deep3321