gravity-toolkit安装和使用笔记整理一
安装
软件
安装anaconda和jupyter notebook,并在conda中创建虚拟环境,命名为grace,创建虚拟环境见[[Anaconda安装与环境配置]]
工具包
https://github.com/tsutterley/gravity-toolkit
https://github.com/tsutterley/geoid-toolkit/
https://github.com/tsutterley/read-GRACE-geocenter
环境
ubuntu16.04
依赖
conda激活grace环境,安装依赖。
激活:conda activate grace
安装:conda install -c conda-forge package_name
根目录(gravity-toolkit)
参照github作者中的gravity-toolkit/README.rst#dependencies安装依赖,包括
- numpy: Scientific Computing Tools For Python
- scipy: Scientific Tools for Python
- dateutil: powerful extensions to datetime
- PyYAML: YAML parser and emitter for Python
- lxml: processing XML and HTML in Python
- future: Compatibility layer between Python 2 and Python 3
- matplotlib: Python 2D plotting library
- cartopy: Python package designed for geospatial data processing
- netCDF4: Python interface to the netCDF C library
- h5py: Python interface for Hierarchal Data Format 5 (HDF5)
- geoid-toolkit: Python utilities for calculating geoid heights from static gravity field coefficients
参照github作者中的gravity-toolkit/requirements.txt安装第三方库,包括
- boto3
- future
- lxml
- matplotlib
- numpy
- python-dateutil
- pyyaml
- scipy
.binder文件夹
github中作者中的gravity-toolkit/.binder/environment.yml中的依赖,详细信息如下。
name: gravity_toolkit
channels:
- conda-forge
dependencies:
- boto3
- cartopy
- future
- h5py
- ipywidgets>=7.6,<8.0(=7.7.5)
- ipympl
- jupyter
- jupyterlab=3
- jupyterlab_widgets
- lxml
- markupsafe==2.0.1
- matplotlib
- netCDF4
- notebook
- numpy
- python>=3.6
- python-dateutil
- pyyaml
- scipy
- tk
- pip
- pip:
.github/workflows
github中作者中的gravity-toolkit/.github/workflows/python-request.yml中的安装依赖,详细信息如下。
此工作流将安装 Python 依赖项、运行测试并使用各种 Python 版本进行 lint。
name: Python on pull request
on:
pull_request:jobs:
build:1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43runs-on: ${{ matrix.os }}
strategy:
matrix:
os: [ubuntu-latest, macos-latest, windows-latest]
python-version: [3.8]
env:
OS: ${{ matrix.os }}
PYTHON: ${{ matrix.python-version }}
defaults:
run:
shell: bash -l {0}
steps:
- uses: actions/checkout@v2
- name: Set up conda ${{ matrix.python-version }}
uses: conda-incubator/setup-miniconda@v2
with:
auto-update-conda: true
python-version: ${{ matrix.python-version }}
activate-environment: gravity_toolkit
environment-file: .binder/environment.yml
- name: Create conda Test Environment
run: |
conda install flake8 pytest pytest-cov cython
pip install git+https://github.com/tsutterley/read-GRACE-geocenter.git
- name: Lint with flake8
run: |
# stop the build if there are Python syntax errors or undefined names
flake8 . --count --select=E9,F63,F7,F82 --show-source --statistics
# exit-zero treats all errors as warnings. The GitHub editor is 127 chars wide
flake8 . --count --exit-zero --max-complexity=10 --max-line-length=127 --statistics
- name: Test with pytest
run: |
pip install --no-deps .
pytest --verbose --capture=no --cov=./ --cov-report=xml \
--username=${{ secrets.EARTHDATA_USERNAME }} \
--password=${{ secrets.EARTHDATA_PASSWORD }} \
--webdav=${{ secrets.PODAAC_PASSWORD }}
- name: Archive code coverage results
uses: actions/upload-artifact@v2
with:
name: code-coverage-report
path: ./coverage.xml
.doc文件夹
github中作者中的gravity-toolkit/doc/environment.yml安装doc 环境,包括下列库。安装命令:
conda install -c conda-forge package_namename: gravity-docs
channels:- conda-forge
dependencies: - docutils<0.18
- fontconfig
- fonttools
- freetype
- future
- graphviz
- lxml
- markupsafe==2.0.1
- numpy
- numpydoc
- pip
- python>=3.6
- python-dateutil
- pyyaml
- scipy
- sphinx
- sphinx_rtd_theme
- pip:
- sphinx-argparse>=0.4
- ..
- conda-forge
github中作者中的gravity-toolkit/doc/source/getting_started/Citations.rst中的依赖,包括下列库。
- cartopy: Python package designed for geospatial data processing
- future: Compatibility layer between Python 2 and Python 3
- h5py: Python interface for Hierarchal Data Format 5 (HDF5)
- ipywidgets: interactive HTML widgets for Jupyter notebooks and IPython
- lxml: processing XML and HTML in Python
- matplotlib: Python 2D plotting library
- netCDF4: Python interface to the netCDF C library
- numpy: Scientific Computing Tools For Python
- python-dateutil: powerful extensions to datetime
- PyYAML: YAML parser and emitter for Python
- scipy: Scientific Tools for Python
- tkinter: Python interface to the Tcl/Tk GUI toolkit
安装
pip 安装(或选择下面的setup安装)
python3 -m pip install –user git+https://github.com/tsutterley/read-GRACE-geocenter.git
python3 -m pip install –user git+https://github.com/tsutterley/geoid-toolkit.git
python3 -m pip install –user git+https://github.com/tsutterley/gravity-toolkit
setup安装
进入gravity-toolkit文件夹(setup.py)同级目录,运行python setup.py install
同理,将read-GRACE-geocenter和geoid-toolkit拷贝入gravity-toolkit文件夹,运行python setup.py install
拷贝
将github上下载的文件夹中的script文件夹拷贝到~/anaconda3/envs/grace/lib/python3.8/site-packages/gravity_toolkit-1.2.0-py3.8.egg/gravity_toolkit 文件夹下便于直接访问script下的函数。
环境变量设置
将gravity_toolkit、gravity_toolkit/scripts和geoid_toolkit添加到环境变量(/.bashrc)中。
1 | <<< GRACE conda initialize <<< |
添加完成后,终端执行source ~/.bashrc
测试
终端执行cnes_grace_sync.py --help和podaac_cumulus.py --help
1 | podaac_cumulus.py --directory="/home/manasakura/draft" --release RL06 |
备注
setup安装后,在conda虚拟环境中就已存在該工具包,路径为~/anaconda3/envs/grace/lib/python3.8/site-packages,在调用工具包中的函数时实际上是调用site-packages中的函数,而不是从github上下载的文件夹中的函数,所以如果按照github文件夹的路径进行函数访问将不会访问到。
学习笔记
文档学习
doc文件夹
doc学习顺序可按照该文档进行
函数用法可查看readdocs.io和api_reference
gravity_toolkit文件夹
SLR文件夹
将C20.py, CS2.py, C30.py, C40.py, C50.py计算出的球协系数值(去除AOD)与matlab中计算出的进行对比,二者答案一致(只校对了GRACE_months 1~4月,对应2002年1月~2002年4月),matlab的计算值保存为~/coding/gravity_workspace/myworkspace/cs2m_c30_c40_c50_gracemonth_1_4_check.mat
C20.py
C20_RL06.txt(PROC=CSR)
SLR.C20中的data变量不是直接读取的C20_RL06.txt中的Column 2中的C20,而是将第二列的C20数据减去Column 5中的AOD产品,详细信息查看原文件中的comment如下。
The RL-06 background gravity model includes solid earth and ocean tides, solid earth and ocean pole tides, and the Atmosphere-Ocean De-aliasing (AOD1B) product. However, the monthly mean of the AOD model has been restored; subtract Column 5 to remove it.
源代码如下:
1 | dinput['time'] = file_input['time'] |
CS2.py
C21(22)_S21(22)_RL06.txt(PROC=CSR)`
读取的CS21/CS22是文件中SLR CS21/CS22(Column 2,3)减去AOD(大气-海洋去混叠,Column 6,7)之后的CS21/CS22,AOD简述可查看Atmosphere-Ocean De-aliasing For GRACE-FO - NASA/ADS 和 Evaluation of high-frequency oceanographic signal in GRACE data: Implications for de-aliasing
大气-海洋去锯齿 (AOD) 产品是一组 Stokes 系数,表示由于大气-海洋质量分布变化引起的非潮汐引力的时间效应。它被用作处理数据流的力模型,以防止高频大气和海洋运动的影响混叠到月解中。
源代码如下:
1 | dinput['time'] = content['time'].copy() |
C30.py
CSR_Monthly_5x5_Gravity_Harmonics.txt(PROC=CSR)
利用read_SLR_harmonics.py计算C30完整球协系数,并返回C30完整球协系数,GRACE_month为从2002.0起算的月份(见time.py中的calendar_to_grace函数)。从GGMO5C平均重力场模型(头文件中)和SLR观测值(正文,系数以相对于平均重力场的变化形式给出,已经去除AOD)相加求C30完整球协系数,并将求得的C30完整球协系数作为返回值。
核心代码如下:
1 | #### CSR_Monthly_5x5_Gravity_Harmonics.txt |
C40.py
CSR_Monthly_5x5_Gravity_Harmonics.txt(PROC=CSR)
同C30.py的方法计算C40完整球协系数。
1 | #### CSR_Monthly_5x5_Gravity_Harmonics.txt 同上C30.py |
C50.py
CSR_Monthly_5x5_Gravity_Harmonics.txt(PROC=CSR)
同C30.py的方法计算C50完整球协系数。
1 | #### CSR_Monthly_5x5_Gravity_Harmonics.txt 同上C30.py |
gen_averaging_kernel.py
生成平均核系数,从而最大限度地减少总误差。
其中输入参数为
INPUTS:
gclm: cosine spherical harmonics of exact averaging kernel
gslm: sine spherical harmonics of exact averaging kernel
eclm: measurement error in the cosine harmonics
eslm: measurement error in the sine harmonics
sigma: variance of the surface mass signal
hw: Gaussian radius of the kernel in kilometers
需要用到的计算公式如下:
区域核函数(exact averaging kernel)
$$
\vartheta(\theta, \phi)=0 \quad outside \quad the \quad basin\
\vartheta(\theta, \phi)=1 \quad inside \quad the \quad basin
$$
求gclm/gslm
$$
\begin{Bmatrix}
\Delta{\vartheta}{lm}^c \ \Delta\hat{\vartheta}{lm}^s
\end{Bmatrix}=
\int \vartheta(\theta,\phi) \widetilde{P}_{lm}(cos\theta)
\begin{Bmatrix}
cosm\phi \ sinm\phi
\end{Bmatrix}d\Omega
$$
离散形式为
$$
\begin{Bmatrix}
\Delta{\vartheta}{lm}^c \ \Delta\hat{\vartheta}{lm}^s
\end{Bmatrix}=
\sum_{i=1}^{180} \sum_{j=1}^{360} \vartheta(\theta_i,\lambda_j)\widetilde P_{lm}(cos\theta_i)sin(m \lambda_j)
\begin{Bmatrix}
cosm\phi \ sinm\phi
\end{Bmatrix}
sin \theta_i \Delta \theta_i \Delta \lambda_j
$$
附上$\vartheta(\theta, \phi)$的球谐展开形式
$$
\vartheta(\theta,\phi) = \frac{1}{4\pi}
\sum_{l=0}^{\infty}\sum_{m=0}^l \widetilde{P}{lm}(cos\theta)(\vartheta{lm}^c \Delta C+\vartheta_{lm}^s \Delta S)
$$
计算Wlms:
gen_disc_load.py
计算均匀 disc load(负荷,与mass含义相近)的重力(gravitational)球谐系数。
gen_harmonics.py
gen_harmonics.py函数进行球谐系数展开主要是利用下列公式:
$$
\Delta C_{lm}=\frac{1}{4\pi} \sum_{i=1}^{180} \sum_{j=1}^{360}\Delta \sigma(\theta_i,\lambda_j)P_{lm}(cos\theta_i)cos(m \lambda_j)sin \theta_i \Delta \theta_i \Delta \lambda_j
$$
$$
\Delta S_{lm}=\frac{1}{4\pi} \sum_{i=1}^{180} \sum_{j=1}^{360}\Delta \sigma(\theta_i,\lambda_j)P_{lm}(cos\theta_i)sin(m \lambda_j)sin \theta_i \Delta \theta_i \Delta \lambda_j
$$
其中,
$$
\Delta \theta = \Delta \lambda = \pi/180
$$
上面公式与Chen(2015)中公式有所不同,Chen(2015)公式如下:
$$
\Delta C_{lm}=\frac{3}{4\pi \rho_E a} \frac{k_l + 1}{2l+1} \sum_{i=1}^{180} \sum_{j=1}^{360}\Delta \sigma(\theta_i,\lambda_j)P_{lm}(cos\theta_i)cos(m \lambda_j)sin \theta_i \Delta \theta_i \Delta \lambda_j
$$
$$
\Delta S_{lm}=\frac{3}{4\pi \rho_E a} \frac{k_l + 1}{2l+1} \sum_{i=1}^{180} \sum_{j=1}^{360}\Delta \sigma(\theta_i,\lambda_j)P_{lm}(cos\theta_i)sin(m \lambda_j)sin \theta_i \Delta \theta_i \Delta \lambda_j
$$
将空间域的数据转化为球协系数.
1 | def demo2(): |
在上述代码中,grid_dir路径指向的文件是由[GRACE-Spatial-Maps.ipynb]文件生成的grid对象,包含计算出的等效水高格网。gen_stokes函数可将該格网(二维)展开为球谐系数,其计算结果与matlab包中的grid2cs.m计算结果相同。matlab代码如下:
1 | grid_dir = '~/coding/gravity_workspace/gwrks0628/CSR_RL06_GSM_ICE6G-D_High_Res_wCSR_C20_wCSR_21_wCSR_22_wCSR_C30_wCSR_C40_wCSR_C50_wTellus_DEG1_cmwe_L60M60_r300km_FL_004-248.nc';; |
需要注意的是,在利用matlab包进行计算时,grid单位换算成了m(grid_data_temp3/100),上面两个计算结果相同,结果如下。
备注:该函数不涉及units类的引入和factor的计算。
gen_stokes.py
将空间域的数据转化为球协系数,可在ocean_stokes.py中查看其如何使用。
公式引用自Chen(2015) ,计算公式如下,
$$
\Delta C_{lm}=\frac{3}{4\pi \rho_E a} \frac{k_l + 1}{2l+1} \sum_{i=1}^{180} \sum_{j=1}^{360}\Delta \sigma(\theta_i,\lambda_j)P_{lm}(cos\theta_i)cos(m \lambda_j)sin \theta_i \Delta \theta_i \Delta \lambda_j
$$
$$
\Delta S_{lm}=\frac{3}{4\pi \rho_E a} \frac{k_l + 1}{2l+1} \sum_{i=1}^{180} \sum_{j=1}^{360}\Delta \sigma(\theta_i,\lambda_j)P_{lm}(cos\theta_i)sin(m \lambda_j)sin \theta_i \Delta \theta_i \Delta \lambda_j
$$
因为
$$
M_e = \rho_e V = \frac{4 \pi a^3 \rho_e}{3}
$$
上面公式等价于下式,
$$
\Delta C_{lm}=\frac{a^2}{M_e} \frac{k_l + 1}{2l+1} \sum_{i=1}^{180} \sum_{j=1}^{360}\Delta \sigma(\theta_i,\lambda_j)P_{lm}(cos\theta_i)cos(m \lambda_j)sin \theta_i \Delta \theta_i \Delta \lambda_j
$$
$$
\Delta S_{lm}=\frac{a^2}{M_e} \frac{k_l + 1}{2l+1} \sum_{i=1}^{180} \sum_{j=1}^{360}\Delta \sigma(\theta_i,\lambda_j)P_{lm}(cos\theta_i)sin(m \lambda_j)sin \theta_i \Delta \theta_i \Delta \lambda_j
$$
核心实现代码如下
1 | #### gen_stokes.py |
1 | #### units.py |
使用 gen_harmonics.py中使用过的同种grid格网数据,进行球谐系数展开,代码如下。
1 | def load_lovenumbers(): |
运行结果如下
grace_date.py
相关介绍查看test_gravity_notebook.ipynb。
grace_find_months.py
相关介绍查看test_gravity_notebook.ipynb。
grace_months_index.py
相关介绍查看test_gravity_notebook.ipynb。
grace_input_months.py
读取GRACE/GRACE- fo文件中指定的球谐l(阶数)和m(次数)以及指定的日期范围。
改正包括:
一阶项替换(如果指定)。
用单反值替换C20(如果指定)。
用179+月份的单反值替换C21/S21/C22/S22/C30/C50(如果指定)。
更正使用GAE, GAF和GAG文件的ECMWF大气“跳跃”。
Wahr et al.(2015)对极潮漂移的修正。
疑问:該函数中CS21/CS22/C30/C40/C50项为什么要设置当grace_month大于179(源码中为 grace_month > 176)时才能用SLR观测值替换GRACE观测值,请问是否在哪篇文献中有所提及,是否可以解答或者提供一下文献链接呢?代码如下(此处仅展示C21项的替换代码,S21/CS22/C30/C40/C50代码基本相同)。
1 | for i,grace_month in enumerate(months): |
geocenter.py
from_tellus()
读取一阶项文件TN-13_GEOC_CSR_RL06.txt,不做处理,详细用法见test_gravity_notebook.ipynb.
harmonics.py
drift(self, t, epoch=2003.3)
将球协系数速度场按照时间积分计算漂移。
核心代码
1 | # # gravity_test_substep.py |
from_dict(self, d, **kwargs)
将字典转化为harmonics类型。
用法
1 | Ylms = grace_input_months(base_dir, PROC=PROC, DREL=DREL, DSET=DREL, LMAX=60, start_mon=4, end_mon=24, |
mean(self, apply=False, indices=Ellipsis)
执行后就会更新GRACE_Ylms内的变量,返回值为球协系数均值。
用法
1 | GRACE_Ylms.mean(apply=True) |
ocean_stokes.py
读取land-sea mask文件并转化为球协系数。
ocean_stokes(LANDMASK, LMAX, MMAX=None, LOVE=None, VARNAME=’LSMASK’, SIMPLIFY=False)
读取landsea.nc文件
下载源:https://www.ncl.ucar.edu/Applications/Data/cdf/landsea.nc 。
1x1 degree mask distributed from UCAR as part of NCL。
landsea.nc文件中的变量名包括lon,lat和LSMASK三类,可使用ncview landsea.nc进行查看。
landsea.nc中各值的含义:
0: ocean
1:land
2:lake
3:small island
4:ice shelf
ocean_stokes代码使用如下:
1 | from gravity_toolkit import ocean_stokes |
ocean_stokes函数会调用spatial.py中的spatial.from_netCDF4()函数,主要用于读取landsea.nc文件,代码如下:
1 | # # ocean_stokes.py |
ocean_stokes函数还会调用gen_stokes.py中的gen_stokes()函数,用于将空间域的数据转化为球协系数,代码如下:
1 | # # ocean_stokes.py |
上一段代码可简单表达为制作海洋掩膜(海洋部分的值为1),并转化为球协系数。
read_GRACE_harmonics.py
读取GRACE/GRACE-FO Level-2 数据。用法见test_gravity_notebook.ipynb。
read_love_numbers.py
load love_numbers
Load Love Numbers match expected for reference frame。用法见test_gravity_notebook.ipynb。
load Load_Love2_CE.dat
Gegout (2005) Load Love Numbers。用法见test_gravity_notebook.ipynb。
load PREM-LLNs-truncated.dat
Wang et al. (2012) Load Love Numbers。用法见test_gravity_notebook.ipynb。
read_GIA_model.py
读取GIA文件(球协系数)。
read_GIA_model(input_file, GIA=None, MMAX=None, DATAFORM=None, **kwargs)
从文件中(ICE-6G_High_Res_Stokes_trend.txt)直接读取GIA球协系数值(GRACE Approximation)。用法见test_gravity_notebook.ipynb。
gia.from_GIA(self, filename, **kwargs)
从文件中(ICE-6G_High_Res_Stokes_trend.txt)直接读取GIA球协系数值(GRACE Approximation)。用法见test_gravity_notebook.ipynb。
spatial.py
对空间数据进行读、写等操作。
spatial.from_netCDF4(self, filename, **kwargs)
读取nc文件。
landsea.nc
下载:https://www.ncl.ucar.edu/Applications/Data/cdf/landsea.nc
landsea.nc文件中包含lon, lat, LSMASK三个变量,该文件可利用ncview可视化查看,查看命令ncview landsea.nc。
核心代码:
1 | # # ocean_stokes.py |
from_netCDF4()函数返回值为landsea(spatial类型),包含attributes, data, extent, filename, lon, lat, spacing等成员变量。data变量中包含的即是landsea.nc文件中的”LSMASK”变量值,下面需要对data变量多加以说明。
data:180×360的ndarray类型的矩阵,上半矩阵为南半球,下半矩阵为北半球,左半矩阵为东半球,右半矩阵为西半球。即是以0度经线和南纬90度纬线的交叉点为坐标原点建立坐标系,横坐标为i,纵坐标为j,i越往东值越大,j越往北值越大,用numpy读取該矩阵也是同理,按照此坐标系可确定矩阵每个坐标(i,j)所对应的地理坐标。
scripts文件夹
time.py
calendar_to_grace(year,month=1,around=np.floor)
**comments:**convert calendar dates to GRACE/GRACE-FO months
1 | grace_month = around(12.0*(year - 2002.0)) + month |