microproduct/vegetationHeight-L-SAR/SatelliteOrbit.py

136 lines
5.1 KiB
Python
Raw Normal View History

2023-08-28 10:17:29 +00:00
''' 卫星轨道模型
根据卫星轨道节点生成对应的卫星轨道模型
整个卫星轨道模型封装成一个单独类
'''
from os import times
from time import time
import numpy as np
import util
def ReconstructionSatelliteOrbit(GPSPoints_list,starttime=1262275200.0):
'''
构建卫星轨道
args:
GPSPoints_list:卫星轨道点
starttime:起算时间默认设置为2010年1月1日0时0分0秒
'''
if len(GPSPoints_list)>16:
SatelliteOrbitModel=SatelliteOrbit_FitPoly()
if SatelliteOrbitModel.ReconstructionSatelliteOrbit(GPSPoints_list,starttime=starttime) is None:
return None
return SatelliteOrbitModel
class SatelliteOrbit(object):
def __init__(self) -> None:
super().__init__()
self.__starttime=1262275200.0
pass
def get_starttime(self):
'''
返回卫星轨道时间起算点
'''
return self.__starttime
def ReconstructionSatelliteOrbit(self,GPSPoints_list):
'''
重建卫星轨道使用多项式拟合法
args:
GPSPoints_list:GPS卫星轨道点
return
SatelliteOrbitModel 卫星轨道模型
'''
self.SatelliteOrbitModel=None
pass
pass
def SatelliteSpaceState(self,time_float):
'''
根据时间戳返回对应时间的卫星的轨迹状态
args:
time_float:时间戳
return
State_list:[time,Xp,Yp,Zp,Vx,Vy,Vz]
'''
return None
class SatelliteOrbit_FitPoly(SatelliteOrbit):
'''
继承于SatelliteOribit类为拟合多项式实现方法
'''
def __init__(self) -> None:
super().__init__()
def ReconstructionSatelliteOrbit(self,GPSPoints_list,starttime=1262275200.0):
if len(GPSPoints_list)>16:
# 多项式的节点数理论上是超过4个可以起算这里为了精度选择16个点起算。
# 多项式 AX=Y ==> A=X'X)^X'Y其中 A 为待求系数X为变量Y为因变量
# 这里使用三次项多项式共有6组参数。
# 声明自变量,因变量,系数矩阵
self.__starttime=starttime
record_count=len(GPSPoints_list)
time_arr=np.zeros((record_count,1),dtype=np.float64) # 使用np.float64只是为了精度高些如果32位也能满足需求请用32
state_arr=np.zeros((record_count,6),dtype=np.float64)
A_arr=np.zeros((5,6),dtype=np.float64)
# 将点记录转换为自变量矩阵、因变量矩阵
for i in range(record_count):
GPSPoint=GPSPoints_list[i]
time_arr[i,0]=GPSPoint[0]-self.__starttime
state_arr[i,:]=np.array(GPSPoint[1:]).reshape(1,6)
# 使用最小二乘法,求解系数
X=np.concatenate([np.ones((record_count,1),dtype=np.float64),time_arr,time_arr**2,time_arr**3,time_arr**4],axis=1)
for i in range(6):
Y=state_arr[:,i]
A_arr[:,i]=np.matmul(np.matmul(np.linalg.inv(np.matmul(X.T,X)),X.T),Y).reshape(1,5) #
self.A_arr=A_arr
return A_arr # shape 6x4
else:
self.A_arr=None
return None
def SatelliteSpaceState(self,time_float):
'''
根据时间戳返回对应时间的卫星的轨迹状态会自动计算与起算时间之差
args:
time_float:时间戳
return
State_list:[time,Xp,Yp,Zp,Vx,Vy,Vz]
'''
if self.A_arr is None:
return None
time_float=time_float-self.__starttime
time_arr=np.ones((1,5),dtype=np.float)
time_arr[0,0]=time_arr[0,0]
time_arr[0,1]=time_arr[0,1]*time_float
time_arr[0,2]=time_arr[0,2]*time_float**2
time_arr[0,3]=time_arr[0,3]*time_float**3
time_arr[0,4]=time_arr[0,4]*time_float**4
SatelliteState_xyz_Vxyz_arr=np.matmul(time_arr,self.A_arr).reshape(1,6)
return np.concatenate([np.array(time_float+self.__starttime).reshape(1,1),SatelliteState_xyz_Vxyz_arr],axis=1)
def getSatelliteSpaceState(self,time_array):
'''
根据时间戳矩阵返回对应时刻的卫星空间状态位置速度且会自动计算与起算时间之差
args:
time_array:nparray nx1 时间戳
return:
SatellitSpaceStateArray:nparray nx6 状态时间
'''
if self.A_arr is None:
return None # 返回None,表示没有结果
A=np.transpose(self.A_arr,(1,0)) # shape 4x6
timeRelative1=time_array-self.__starttime # 返回相对值
n=timeRelative1.shape[0]
timeRelative=np.ones((n,5))
timeRelative[:,1]=timeRelative1
timeRelative[:,2]=timeRelative1**2
timeRelative[:,3]=timeRelative1**3
timeRelative[:,4]=timeRelative1**4
SatelliteSpaceStateArray=np.matmul(timeRelative,A) # nx6
return SatelliteSpaceStateArray # 位置矩阵
pass