我所基于的代碼版本是RTKlib 2.4.3的一個拓展版本RTKexplore Demo5,這個版本主要針對低成本的GNSS進行了一些改進完善。
pppos
extern void pppos(rtk_t *rtk, const obsd_t *obs, int n, const nav_t *nav)
- 所在文件:ppp.c
- 功能說明:PPP處理
- 參數說明:
args: IO rtk_t *rtk rtk solution structure
I const obsd_t *obs 當前歷元觀測值
I int n 當前移動站觀測值數目
I const nav_t *nav 星歷
- 調用udstate_ppp函數進行卡爾曼濾波的一步預測;
- 調用satposs函數計算衛(wèi)星位置;
- 如果在配置中選擇排除block IIA衛(wèi)星,調用testeclipse函數,將這些衛(wèi)星的位置、速度置0;
- 如果在配置中選擇潮汐修正,調用tidedisp函數進行潮汐修正;
- 調用ppp_res函數計算預測值與量測值之間的殘差;
- 待用filter函數進行卡爾曼濾波的量測更新;
- 調用ppp_res函數計算量測更新后的殘差;
- 調用ppp_ar進行整周模糊度結算,并調用ppp_res進行殘差計算;
- 調用update_stat更新輸入、輸出參數rtk solution的狀態(tài)
- 需要注意的是,步驟8中ppp_ar是個空函數,返回值為0,因此實際后面的ppp_res函數也不會被調用。如此來看,實際PPP的解為通過卡爾曼濾波得到的浮點解。
- satposs和相對定位中的函數一致,不再進行解析,可參考RTKLIB源碼解析——單點定位
udstate_ppp
static void udstate_ppp(rtk_t *rtk, const obsd_t *obs, int n, const nav_t *nav)
- 所在文件:ppp.c
- 功能說明:進行卡爾曼濾波的一步預測,更新rtk->x狀態(tài)量值
- 參數說明:
args: IO rtk_t *rtk rtk solution structure
I const obsd_t *obs 當前歷元觀測值
I int n 當前移動站觀測值數目
I const nav_t *nav 星歷
- 調用udpos_ppp函數位置、速度、加速度狀態(tài)量 rtk->x以及相應協(xié)方差陣 rtk->P的更新;
- 調用udclk_ppp函數,更新鐘差狀態(tài)量(以gpst為基準);
- 如果在配置中選擇的對流層模型為ZTD estimation或者ZTD+grad estimation,調用udtrop_ppp進行對流層參數狀態(tài)量的更新;
- 如果在配置中選擇電離層模型為estimation,調用udiono_ppp函數,更新電離層誤差參數狀態(tài)量;
- 如果選擇的頻率數>=3,則進行L5 dcb狀態(tài)量的更新;
- 調用udbias_ppp函數進行相位bias狀態(tài)量的更新。
- 參考RTklib manual 來看,PPP算法中使用的量測量為“無電離層組合的偽距、載波相位”,所以配置中可以將電離層模型選擇為“Iono free LC”。通過參考RTKexplorer博客Exploring kinematic single-receiver solutions with RTKLIB and the u-blox F9P. 中的配置,對流層模型應該至少配置為ZTD estimation。我在之后的博客中會測試一下不同的PPP配置對精度有多大的影響。
- 參考 RTKLIB Manual 可知狀態(tài)量包括位置、速度、接收機鐘差、對流層參數、衛(wèi)星相位偏差;
- udpos_ppp、udtrop_ppp、udiono_ppp函數與之前相對定位中udpos、udtrop、udion函數流程基本一致,就不再詳細解釋,具體可參考RTKlib相對定位源碼解析: udstate函數。由于udbias_ppp和相對定位中不同,因此在下文中進行解析。
udbias_ppp
static void udbias_ppp(rtk_t *rtk, const obsd_t *obs, int n, const nav_t *nav)
- 所在文件:ppp.c
- 功能說明:進行相位偏差狀態(tài)量和協(xié)方差陣的一步預測
- 參數說明:
args: IO rtk_t *rtk rtk solution structure
I const obsd_t *obs 當前歷元觀測值
I int n 當前移動站觀測值數目
I const nav_t *nav 星歷
- 首先是對所有共視星進行周跳檢測:調用了detslp_ll函數,根據LLI來判斷基站和移動站周跳;然后調用detslp_gf利用幾何無關組合進行周跳檢測;最后調用了detslp_gf_mw函數進行周跳檢測。對RTKlib的周跳檢測函數,我專門寫了一篇博客解析RTKlib源碼解析:ppp和rtkpost中的周跳檢測函數
- 對所有衛(wèi)星進行循環(huán),判斷是否需要重置單差相位偏移狀態(tài)量。如果所配置的AR的模式為instantaneous(實際由于當前PPP中使用的是浮點解,通常將PPP的AR配置為OFF),或者衛(wèi)星載波相位的中斷次數大于配置中所設置的最大次數,則將單差相位偏移狀態(tài)量重置為0;
- 對每一組觀測數據,調用 corr_meas函數對偽距、載波相位進行修正,并計算無電離層組合的偽距、載波相位量測量Pc和Lc;
- 將每顆衛(wèi)星的載波相位偏差bias初始化為0,如果電離層模型為電離層無關模型,則直接計算bias[i]=Lc-Pc;否則的話,通過偽距計算電離層延遲ion=(obs[i].P[0]-obs[i].P[l])/(1.0-SQR(lam[l]/lam[0]));由于L1和L2偽距相減后,只剩下L1和L2的電離層誤差之差,以及偽距噪聲項,因此由此計算出來的電離層誤差實際包含了偽距噪聲,誤差相對較大。利用修正電離層誤差后的偽距和載波相位之差計算bias: bias[i]=L[f]-P[f]+2.0ionSQR(lam[f]/lam[0]);
- 計算每顆衛(wèi)星的bias與載波相位偏差狀態(tài)量rtk->x之間的偏差offset之和;
- 在原有的載波相位偏差狀態(tài)量上加上offset的平均值,以此來作為載波相位偏差一步預測值:rtk->x[j]+=offset/k;
7.對每顆衛(wèi)星循環(huán),更新一步預測協(xié)方差陣,對有周跳的衛(wèi)星、或者沒有初始化載波相位偏差狀態(tài)量的衛(wèi)星,用之前計算的bias值重新初始化載波相位偏差狀態(tài)量。
corr_meas
static void corr_meas(const obsd_t *obs, const nav_t *nav, const double *azel,
const prcopt_t *opt, const double *dantr,
const double *dants, double phw, double *L, double *P,
double *Lc, double *Pc)
- 所在文件:ppp.c
- 功能說明:計算經過接收機天線修正、相位纏繞校正、SSR修正或者dcb 修正后的偽距、載波相位量測量,并計算無電離層組合的偽距、載波相位值Lc,Pc
- 參數說明:
args: I const obsd_t *obs 當前歷元觀測值
I const nav_t *nav 星歷
I const double *azel 方位角和俯仰角 (rad)
I const prcopt_t *opt 處理選項
I const double *dantr 接收機天線校正值
I const double *dants 衛(wèi)星天線校正值
I double phw 相位纏繞校正值
O double *L 修正后的載波相位
O double *P 修正后的偽距值
O double *Lc 無電離層組合的載波相位值
O double *Pc 無電離層組合的偽距值
- 調用 testsnr函數檢查觀測值的信噪比是否大于mask;
- 對偽距天線修正、相位纏繞校正,對載波相位進行天線修正;
- 如果星歷類型是broadcast + SSR_APC或者broadcast + SSR_COM,對偽距值進行ssr 修正;如果是其他星歷類型,進行 DCB 校正;
- 計算無電離層組合的偽距、載波相位值Lc,Pc
ppp_res
static int ppp_res(int post, const obsd_t *obs, int n, const double *rs,
const double *dts, const double *var_rs, const int *svh,
const double *dr, int *exc, const nav_t *nav,
const double *x, rtk_t *rtk, double *v, double *H, double *R,
double *azel)
- 所在文件:ppp.c
- 功能說明:計算載波相位和偽距殘差
- 參數說明:
args: I int post 是否是修正后殘差計算標志
I const obsd_t *obs 當前歷元觀測值
I int n 當前移動站觀測值數目
I const double *dts 衛(wèi)星鐘差
I const double *var_rs 星位置和鐘差的協(xié)方差
I const int *svh 衛(wèi)星健康標志
I const double *dr 地球潮汐位移
IO int *exc 衛(wèi)星排除標志
I const nav_t *nav 星歷
IO const double *x 狀態(tài)量
IO rtk_t *rtk rtk solution structure
IO double *v 載波相位和偽距殘差
IO double *H 卡爾曼濾波中的觀測矩陣
IO double *R 測量誤差的協(xié)方差矩陣
I const double *azel 方位角和俯仰角 (rad)
- 把衛(wèi)星的有效標志位均置0,rtk->ssat[i].vsat[j]=0;
- 在一步預測值x[i]基礎上加上潮汐修正,作為移動站位置:rr[i]=x[i]+dr[i];
- 對每顆星進行循環(huán),根據移動站位置,計算衛(wèi)星仰角,如果小于設定閾值,排除該衛(wèi)星,并且檢查該衛(wèi)星系統(tǒng)、單點定位衛(wèi)星有效標志、是否在設置中排除,重置排除標志:exc[i]=1;
- 調用model_trop函數計算對流層誤差dtrp,調用model_iono函數計算電離層誤差dion;
- 調用satantpcv函數計算衛(wèi)星天線校正參數dants;調用antmodel函數計算根據接收機天線的相位中心參數計算天線偏移量dantr,該函數在此博客曾進行解析;
- 調用model_phw函數計算相位纏繞校正值rtk->ssat[sat-1].phw;
- 調用corr_meas函數對偽距和載波相位進行修正,得到量測量;
- 計算量測矩陣H和殘差v,相位殘差存放在 rtk->ssat[sat-1].resc中,偽距殘差在rtk->ssat[sat-1].resp中;
- 綜合考慮偽距(載波相位)噪聲、對流層噪聲、電離層噪聲、衛(wèi)星位置鐘差噪聲后,作為量測噪聲;如果是GLONASS衛(wèi)星,在偽距量測噪聲上,還要加上IFB噪聲(頻間差噪聲);
- 如果是 pre-fit,即!post的情況,如果某顆殘差值大于閾值,將這顆星排除;
- 如果post為1,某顆殘差值大于閾值,將這顆星記錄下來;整個循環(huán)結束;
- 如果post為1,找到11步中殘差值最大的那顆星,將其排除。
|