Spacepy安装与使用
最近科研的时候需要用到geopack,这个包本身并不陌生,但是作者的源码是Fortran写的,之后一般在IDL 上使用。第一次学习磁层的时候老师让我去下一个geopack并且画出一张磁力线的图,我当时就对IDL 这门语言产生了抗拒。我认为一个好的语言是方便学习和交流,世界上很多人说英语,所以英语是一门好的语言,很多人说汉语,所以汉语也是一门好的语言。很多人用python,很多人用matlab,但是当遇到IDL的时候,google老师就很难派上用场。 使用范围的狭窄限制了我的自学能力,IDL 的帮助文档看起来真的是一头雾水,而且正版IDL价格不菲,相信它早晚会被淘汰。这篇就记录一下通过spacepy来达到geopack的功能。
关于spacepy的安装
spacepy 官方doc:
https://pythonhosted.org/SpacePy/index.html
spacepy是一个基于python的用于空间科学计算的包,主要用于基本的数据分析和可视化。更新和维护速度虽然很慢,(听师兄说是Boulder的那群人写的)但是查看了git后发现居然还有几个兄弟在默默地维护和更新,比如升级对python3.6的支持等等。真的是想buy them beers!
我使用的是OS 系统,也在Ubuntu系统下成功配置了这个包。虽然是一个简单的python模块,但是有相当多的dependence。
我使用的是Python3.6,最近3.7版本已经发布,还没有测试在这个版本下是否安装成功
配置python环境
配置python环境是一件比较容易的事情,如果想使用pycharm等编译器的话最好有自己独立于系统的环境。使用前可以查看一下当前自己python的位置
➜ ~ which python
/Users/madonglai/anaconda3/bin/python
这是自己配置的环境,具体anaconda使用的方法就不在这里写出。如果是需要在linux服务器上使用,可以通过miniconda或者virtualenv来配置自己的虚拟环境,他们的好处是可以配置自己的环境甚至是python的版本。
之后开始安装spacepy所需要的依赖包
https://pythonhosted.org/SpacePy/dependencies.html
基本上利用pip install 这个神奇的命令都可以完成,唯一需要注意的是CDF这个是需要自己去下的。
依赖都安装好了之后同样可以用pip install spacepy 来安装。运行过程中会自动检测你的依赖是否都安装好了。
当然也可以去git上下载他们一直在更新的包解压后进入目录,然后通过
python setup.py build
python setup.py install
来进行安装。
当然这么简单的安装过程大概率是有bug的!我遇到的一个比较严重的bug就是gfortran的编译器版本问题。安装后需要阅读下是否安装成功,这也是我最后不用pip的原因
Compiler /usr/local/bin/gfortran failed, trying another
Compiler gfortran failed, trying another
irbemlib compile failed. Try a different Fortran compiler? (--fcompiler)
irbemlib这个包的作者,使用了f2p这种简单的把fortran语言转换成python语言的方法,所以需要fortran的编译器,但是如果是通过
brew install gcc
这种方法安装的带有gfortran的版本似乎不能好的编译,而且一般都是安装home brew,不便于卸载gcc,经常会遇到一些权限问题(运行brew doctor 可以方便地查看哪里除了问题)于是
sudo rm -r /usr/local/gfortran /usr/local/bin/gfortran
之后再重新下载一个gfortran问题就解决了。
在Ubuntu下的安装就相对比较顺利,基本步骤也类似,完全可以参照之前的例子或者spacepy的主页来解决。但是在CDF的安装时会出现一点问题,具体问题和解决方法在之后会提到。
关于这个例子
Geopack有很多优点,在spacepy并没有单独的接口,但是Geopack本质上是基于Ts磁场模型计算磁场(还有一些坐标转换。)
本次例子的目的是根据时间和位置,获得空间中任意一点的磁场。在spacepy中有很多完成的接口供我们使用。例如在这个例子中需要使用的包irbempy得到磁场的函数
spacepy.irbempy.get_Bfield(ticks, loci, extMag='T01STORM', options=[1, 0, 0, 0, 0], omnivals=None)
当然第一次使用的时候可能会出问题,因为你并没有下载那个OMNI 的数据,命令行会给出提示,也有可能不会给,下载的时候也会出很多问题,需要多尝试几遍。可以在命令行前加入以下命令
import spacepy.toolbox as spt
spt.update(omni = True)
更新过一次数据库就不用了,本质上这个包是从OMNI 的database那里去下载数据,然后再进行数据处理,OMNI中的数据都是CDF格式,所以之前cdf的安装是必须的。
我也曾经尝试过在Ubuntu16下安装cdf,会出现一点问题,具体问题是环境变量的配置。在make install 之后会有解释文件 definition.B (在安装目录./bin 下),将其最后一行改为
export LD_LIBRARY_PATH=$HOME/Libraries/cdf/cdf37_0-dist/lib:$LD_LIBRARY_PATH
在~/.bashrc中最后加入 .$HOME/Libraries/cdf/cdf37_0-dist/definition.B 然后chmod +x将这个文件变成可执行文件并运行。
以上路径是我瞎写的,需要自己参照自己的路径来使用
数据的一些基本处理
配置好所有的库和下载好数据之后就可以开始进行操作了。所有包的解释都在
https://pythonhosted.org/SpacePy/index.html
可以参照进行阅读,但是有些最新版本的更新在这个网站上没有解释,推荐准确的解释去阅读源代码中的note,这是一个比较好的选择。
import spacepy.time as spt
import spacepy.coordinates as spc
import spacepy.irbempy as ib
import spacepy.toolbox as st
t = spt.Ticktock(['2014-02-02T12:00:00', '2014-02-02T12:10:00'], 'ISO')
y = spc.Coords([[3,3,0],[2,3,0]], 'SM', 'car')
m = ib.get_Bfield(t,y)
print(m)
得出结果如下
{'Blocal': array([ 396.1620274 , 648.43456977]), 'Bvec': array([[ 15.7710819 , -51.64604429, 392.46440735],
[ 16.65412153, -90.57326112, 641.86175761]])}
没有指定参数的时候会按照默认参数得出结果。这个例子中我想得到的是包含外场(TS05)模型的磁场,有趣的是这个模型在spacepy中的简称是T05... 并没有另一位兄弟Sitnov。
Bfield = ib.get_Bfield(dts,ys_GEO,'T05')
Bfield_noe = ib.get_Bfield(dts,ys_GEO,'0')
0代表没有外部场,T05代表外场用的是TS05模型等等,这样就达到了geopack的基础功能。在阅读源码的过程中会发现getfield这个函数只能得到在geo坐标下的磁场!这个是在note里没有写的
实现了第一步,那么画磁力线啊等等等等基于geopack的功能就不难实现了!
还有一些关于坐标转换和时间序列的基础操作,在这里就不去详述了,但毫无疑问这些都是需要注意的事情。python的数组操作虽然有了numpy等一系列的包,但在处理数组和一些函数方面,(比如弧度转角度并不能对整个数组使用)个人感觉还是不如matlab的。
当然spacepy还有很多很多很多的有用的function,之后用到的时候再记录下来。
感想
把一些东西记录下来还是很有趣的,每次在科研或者学习的过程中都会开很多网页,而很多网页都是打开过一遍的。留在脑子里的东西很少,而记录下来应该会对自己有所帮助。
我python的使用还是处在入门阶段,比如spacepy安装的源码有一些就没有看懂,并没有时间去静下心来学习总结,感到很难受。
FORTRAN辣鸡!IDL辣鸡!
网友评论