利用MATLAB读取NetCDF文件

网络通用数据格式(Network Common Data Form, netCDF)是由美国大学大气研究协会(University Corporation for Atmospheric Research, UCAR)的Unidata团队研发,现今已是应用在气象科学领域用于存储数据的常见存储标准,在美国国家海洋大气局(NOAA)、美国国家能源部(DOE)、美国国家航空航天局(NASA)和美国大气研究中心(NCAR)等部门都有广泛应用。
目前,C/C++, Java, Python, MATLAB, R和Ruby等语言都有支持访问netCDF文件的编程接口。本文主要讲述利用MATLAB读取NetCDF文件。本文以美国NOAA的地球系统研究实验室(ESRL)下的物理信息部(PSD)所提供的数据为例进行讲述。

netCDF的数据具有以下特征:

  1. 自描述性(Self-Describing):netCDF文件会包含该数据文件的解释信息;
  2. 便捷性(Portable):netCDF文件可以支持如整型、字符型、浮点型等不同类型的数据存储;
  3. 可伸缩性(Scalable):通过netCDF接口,可以快捷地访问大规模数据集中的数据;
  4. 可附加性(Appendable):通过恰当的结构,数据可以直接附加在已有的netCDF文件之后;
  5. 共享性(Sharable):netCDF可以允许多个访问者同时访问统同一文件;
  6. 可存档性(Archivable):当前版本可以访问所有先前的netCDF文件数据。

一个netCDF文件由以下两部分组成:

  • 头文件(header):包括文件中除数据之外的所有信息——属性(Attributes)、维度(dimensions)和变量(Variables)。
  • 数据(data part):包含变尺寸和定尺寸的数据。

具体的说明我们结合MATLAB接口来看。
函数
在MATLAB中有若干常用的高级函数,使用这些函数可以轻松地从netCDF文件读取数据集或将数据写入到netCDF文件中。以下是常用的函数。

函数名 说明
nccreate 在netCDF文件中创建变量
ncdisp 在命令行窗口中显示netCDF数据源内容
ncinfo 返回有关netCDF数据源的信息
ncread 读取netCDF数据源的变量数据
ncreadatt 读取netCDF数据源的属性值
ncwrite 将数据写入netCDF文件
ncwriteatt 将属性写入netCDF文件

下面我们以数据集为例,利用以上部分函数来读取数据集中的数据。

  1. ncdisp
%文件名
FileName = 'uwnd.2004.nc';

%在命令行窗口中显示netCDF数据源内容
ncdisp(FileName)

可以看到命令行中已经打印出了uwnd.2004.nc文件的内容
利用MATLAB读取NetCDF文件_第1张图片
在上图中,我们可以看到netCDF数据文件的属性(Attributes)、维度(dimensions)和变量(Variables)等信息。
其中属性中有名称(title)、描述(description)和历史信息(history)等字段,简要描述了这个数据文件的一些信息。通过description可以看出,该数据集每天有4个采样点。
维度则描述了该数据文件由哪些数据维度组成以及各维度的规模大小。在本文的数据集中,有lon、lat、level和time四个维度。由于2004年有366天,故time维度的大小为366×4=1464。
变量则细致地介绍了各变量的详细信息。包括它们的名称、单位、含义、大小和范围等。我们可以看出各变量代表的含义如下表所示。

变量 含义 数据规模 范围
level 气压水平 17 [1000 10]
lat 维度 73 [90 -90]
lon 经度 144 [0 357.5]
time 时间 1464 [1788216 1796994]
uwnd 风速 144x73x17x1464 [-74.89999 138.3]

最后的uwnd就是该数据文件中实际存储的数据。

  1. ncinfo
%文件名
FileName = 'uwnd.2004.nc';

%查看netCDF数据源的信息
info = ncinfo('uwnd.2004.nc');

我们可以在工作区查看到info的相关信息
利用MATLAB读取NetCDF文件_第2张图片
维度、变量和属性的详细信息可以逐个查看。
利用MATLAB读取NetCDF文件_第3张图片
可以看出ncinfo的功能与ncdisp的功能类似,都是用于查看数据文件的基本信息。

  1. ncread

ncdisp和ncread函数都只能看到数据文件的基本信息,若想要看到各维度的详细信息,还需要调用ncread函数。

%文件名
FileName = 'uwnd.2004.nc';

%读取netCDF数据源中的各变量数据
time = ncread(FileName,'time');
level = ncread(FileName,'level');
lat = ncread(FileName,'lat');
lon = ncread(FileName,'lon');   

我们可以分别看到各维度的信息
利用MATLAB读取NetCDF文件_第4张图片
可以看出,经纬度lon和lat的采样间隔为2.5°,气压水平level的采样间隔则是不均匀的。
值得一提的是,时间维度并没有采用传统的年-月-日等时间格式,而是以一个较大整数来表示,每个时间点的数值实质上是相对于1800年1月1日0点所经过的小时数的计数值。

MATLAB提供了netcdf包,可以直接与netCDF库交互。下面我们演示一下如何利用netcdf包访问netCDF数据文件的数据。

%文件名
FileName = 'uwnd.2004.nc';
%查询位于(32.5°N,112.5°E),气压值为925毫巴的空间点在2004年3月2日至3月4日的uwnd数据
lon = 46;  % 112.5°E
lat = 24;  % 32.5°N
level = 2;  % 925毫巴
timeindex = 4*(31+29+1)+1;  % 起始时间 3月2日0点
period = 12;  % 12个时刻点

uwnd = zeros(period,1);

%打开netCDF数据文件(只读方式)
ncid = netcdf.open(FileName,'NOWRITE');
%获取uwnd数据
varid = 4;
winddata = netcdf.getVar(ncid,varid);
%关闭netCDF数据文件
netcdf.close(ncid);

%获取目标区间数据
uwnd(1:period) = winddata(lon, lat, level, timeindex : timeindex+period-1)

结果如下图所示。
利用MATLAB读取NetCDF文件_第5张图片
以上就是MATLAB利用netcdf包访问netCDF数据文件中数据的方法。

参考文献:

  1. https://www.unidata.ucar.edu/software/netcdf/
  2. https://www.mathworks.com/help/matlab/network-common-data-form.html

你可能感兴趣的:(利用MATLAB读取NetCDF文件)