使用GDAL读取HDF,NetCDF等数据集中的数据时,一般需要两个步骤,第一,获取数据集中的子数据集;第二,通过第一步获取的子数据集读取图像数据。一般的HDF图像中会有很多个子数据集,比如常用的MODIS数据,使用Envi打开会弹出下面的对话框来让用户选择需要打开的子数据集(如图1)。

图1 Envi打开Modis数据

从图1中可以看出,Envi是把所有的子数据集的波段都进行了列举,不过这点和GDAL读取有点不一样。(这里有个比较疑惑的地方就是,使用GDALInfo获取的子数据一共有46个,而且很多图像大小都不一样,而这里Envi所有的波段图像大小都是1354×2030,希望知道的同学告知一下,难道那些小一点的406×271的都不要了?)。

看完Envi的,我们使用GDALInfo工具查看这个数据的信息,输出的内容如下:

Driver: HDF4/Hierarchical Data Format Release 4
Files: F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf
Size is 512, 512
Coordinate System is `'
Metadata:% Dead Detector EV Data=0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0此处省略NNNNNNNNNNNNNNNNNNNNNNNNNNNNNNN多字........................................SOUTHBOUNDINGCOORDINATE=27.4153536499348VERSIONID=5WESTBOUNDINGCOORDINATE=106.240739628195
Subdatasets:SUBDATASET_1_NAME=HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:EV_1KM_RefSBSUBDATASET_1_DESC=[15x2030x1354] EV_1KM_RefSB MODIS_SWATH_Type_L1B (16-bit unsigned integer)SUBDATASET_2_NAME=HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:EV_1KM_RefSB_Uncert_IndexesSUBDATASET_2_DESC=[15x2030x1354] EV_1KM_RefSB_Uncert_Indexes MODIS_SWATH_Type_L1B (8-bit unsigned integer)SUBDATASET_3_NAME=HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:EV_1KM_EmissiveSUBDATASET_3_DESC=[16x2030x1354] EV_1KM_Emissive MODIS_SWATH_Type_L1B (16-bit unsigned integer)SUBDATASET_4_NAME=HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:EV_1KM_Emissive_Uncert_IndexesSUBDATASET_4_DESC=[16x2030x1354] EV_1KM_Emissive_Uncert_Indexes MODIS_SWATH_Type_L1B (8-bit unsigned integer)SUBDATASET_5_NAME=HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:EV_250_Aggr1km_RefSBSUBDATASET_5_DESC=[2x2030x1354] EV_250_Aggr1km_RefSB MODIS_SWATH_Type_L1B (16-bit unsigned integer)SUBDATASET_6_NAME=HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:EV_250_Aggr1km_RefSB_Uncert_IndexesSUBDATASET_6_DESC=[2x2030x1354] EV_250_Aggr1km_RefSB_Uncert_Indexes MODIS_SWATH_Type_L1B (8-bit unsigned integer)SUBDATASET_7_NAME=HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:EV_250_Aggr1km_RefSB_Samples_UsedSUBDATASET_7_DESC=[2x2030x1354] EV_250_Aggr1km_RefSB_Samples_Used MODIS_SWATH_Type_L1B (8-bit integer)SUBDATASET_8_NAME=HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:EV_500_Aggr1km_RefSBSUBDATASET_8_DESC=[5x2030x1354] EV_500_Aggr1km_RefSB MODIS_SWATH_Type_L1B (16-bit unsigned integer)SUBDATASET_9_NAME=HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:EV_500_Aggr1km_RefSB_Uncert_IndexesSUBDATASET_9_DESC=[5x2030x1354] EV_500_Aggr1km_RefSB_Uncert_Indexes MODIS_SWATH_Type_L1B (8-bit unsigned integer)SUBDATASET_10_NAME=HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:EV_500_Aggr1km_RefSB_Samples_UsedSUBDATASET_10_DESC=[5x2030x1354] EV_500_Aggr1km_RefSB_Samples_Used MODIS_SWATH_Type_L1B (8-bit integer)SUBDATASET_11_NAME=HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:HeightSUBDATASET_11_DESC=[406x271] Height MODIS_SWATH_Type_L1B (16-bit integer)SUBDATASET_12_NAME=HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:SensorZenithSUBDATASET_12_DESC=[406x271] SensorZenith MODIS_SWATH_Type_L1B (16-bit integer)SUBDATASET_13_NAME=HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:SensorAzimuthSUBDATASET_13_DESC=[406x271] SensorAzimuth MODIS_SWATH_Type_L1B (16-bit integer)SUBDATASET_14_NAME=HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:RangeSUBDATASET_14_DESC=[406x271] Range MODIS_SWATH_Type_L1B (16-bit unsigned integer)SUBDATASET_15_NAME=HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:SolarZenithSUBDATASET_15_DESC=[406x271] SolarZenith MODIS_SWATH_Type_L1B (16-bit integer)SUBDATASET_16_NAME=HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:SolarAzimuthSUBDATASET_16_DESC=[406x271] SolarAzimuth MODIS_SWATH_Type_L1B (16-bit integer)SUBDATASET_17_NAME=HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:gflagsSUBDATASET_17_DESC=[406x271] gflags MODIS_SWATH_Type_L1B (8-bit unsigned integer)SUBDATASET_18_NAME=HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:EV_Band26SUBDATASET_18_DESC=[2030x1354] EV_Band26 MODIS_SWATH_Type_L1B (16-bit unsigned integer)SUBDATASET_19_NAME=HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:EV_Band26_Uncert_IndexesSUBDATASET_19_DESC=[2030x1354] EV_Band26_Uncert_Indexes MODIS_SWATH_Type_L1B (8-bit unsigned integer)SUBDATASET_20_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":0SUBDATASET_20_DESC=[406x271] Latitude (32-bit floating-point)SUBDATASET_21_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":1SUBDATASET_21_DESC=[406x271] Longitude (32-bit floating-point)SUBDATASET_22_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":2SUBDATASET_22_DESC=[15x2030x1354] EV_1KM_RefSB (16-bit unsigned integer)SUBDATASET_23_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":3SUBDATASET_23_DESC=[15x2030x1354] EV_1KM_RefSB_Uncert_Indexes (8-bit unsigned integer)SUBDATASET_24_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":4SUBDATASET_24_DESC=[16x2030x1354] EV_1KM_Emissive (16-bit unsigned integer)SUBDATASET_25_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":5SUBDATASET_25_DESC=[16x2030x1354] EV_1KM_Emissive_Uncert_Indexes (8-bit unsigned integer)SUBDATASET_26_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":6SUBDATASET_26_DESC=[2x2030x1354] EV_250_Aggr1km_RefSB (16-bit unsigned integer)SUBDATASET_27_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":7SUBDATASET_27_DESC=[2x2030x1354] EV_250_Aggr1km_RefSB_Uncert_Indexes (8-bit unsigned integer)SUBDATASET_28_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":8SUBDATASET_28_DESC=[2x2030x1354] EV_250_Aggr1km_RefSB_Samples_Used (8-bit integer)SUBDATASET_29_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":9SUBDATASET_29_DESC=[5x2030x1354] EV_500_Aggr1km_RefSB (16-bit unsigned integer)SUBDATASET_30_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":10SUBDATASET_30_DESC=[5x2030x1354] EV_500_Aggr1km_RefSB_Uncert_Indexes (8-bit unsigned integer)SUBDATASET_31_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":11SUBDATASET_31_DESC=[5x2030x1354] EV_500_Aggr1km_RefSB_Samples_Used (8-bit integer)SUBDATASET_32_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":12SUBDATASET_32_DESC=[406x271] Height (16-bit integer)SUBDATASET_33_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":13SUBDATASET_33_DESC=[406x271] SensorZenith (16-bit integer)SUBDATASET_34_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":14SUBDATASET_34_DESC=[406x271] SensorAzimuth (16-bit integer)SUBDATASET_35_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":15SUBDATASET_35_DESC=[406x271] Range (16-bit unsigned integer)SUBDATASET_36_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":16SUBDATASET_36_DESC=[406x271] SolarZenith (16-bit integer)SUBDATASET_37_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":17SUBDATASET_37_DESC=[406x271] SolarAzimuth (16-bit integer)SUBDATASET_38_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":18SUBDATASET_38_DESC=[406x271] gflags (8-bit unsigned integer)SUBDATASET_39_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":19SUBDATASET_39_DESC=[2030x1354] EV_Band26 (16-bit unsigned integer)SUBDATASET_40_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":20SUBDATASET_40_DESC=[2030x1354] EV_Band26_Uncert_Indexes (8-bit unsigned integer)SUBDATASET_41_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":21SUBDATASET_41_DESC=[16x10] Noise in Thermal Detectors (8-bit unsigned integer)SUBDATASET_42_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":22SUBDATASET_42_DESC=[16x10] Change in relative responses of thermal detectors (8-bit unsigned integer)SUBDATASET_43_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":23SUBDATASET_43_DESC=[203x16x10] DC Restore Change for Thermal Bands (8-bit integer)SUBDATASET_44_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":24SUBDATASET_44_DESC=[203x2x40] DC Restore Change for Reflective 250m Bands (8-bit integer)SUBDATASET_45_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":25SUBDATASET_45_DESC=[203x5x20] DC Restore Change for Reflective 500m Bands (8-bit integer)SUBDATASET_46_NAME=HDF4_SDS:UNKNOWN:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":26SUBDATASET_46_DESC=[203x15x10] DC Restore Change for Reflective 1km Bands (8-bit integer)
Corner Coordinates:
Upper Left  (    0.0,    0.0)
Lower Left  (    0.0,  512.0)
Upper Right (  512.0,    0.0)
Lower Right (  512.0,  512.0)
Center      (  256.0,  256.0)

从上面的输出信息中可以看出,这个HDF数据其实有46个子数据,从上面的Subdatasets开始,一共有46个子数据集,同时GDAL列举了这些数据的描述信息,包括数据大小波段数以及数据类型。下面以第一个子数据集为例说明一下GDAL输出的这个信息的大致意思,第一个子数据集的描述如下:

  SUBDATASET_1_NAME=HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:EV_1KM_RefSBSUBDATASET_1_DESC=[15x2030x1354] EV_1KM_RefSB MODIS_SWATH_Type_L1B (16-bit unsigned integer)

可以看出,一个子数据集由两行组成,第一行表示这个子数据集的“路径”,这里的路径可以认为是这个子数据集存储在HDF文件中的路径。后面使用GDAL读取数据就要使用这个路径。第二行表示的是对这个子数据的描述信息,比如这里的,15×2030×1354就表示这个子数据有15个波段,长和宽分别是2030和1354。周末的EV_1KM_RefSB MODIS_SWATH_Type_L1B表示的是这个数据的处理级别和类型等,接下来的括弧里面的16-bit unsigned integer表示这个子数据集是个16位的无符号整数。

那么接下来如何使用gdal来获取子数据集里面的图像信息呢,我们还是以gdalinfo这个工具来说明。要获取hdf中每个子数据集的信息,首先要获取hdf中子数据集的路径才行,这个路径就需要上面的SUBDATASET_1_NAM来确定了。还是以第一个子数据集为例,使用的命令行如下,截图如图2所示:

gdalinfo.exe HDF4_EOS:EOS_SWATH:"F:\Data\HDF\MOD021KM.A2010287.0250.005.2010287121743.hdf":MODIS_SWATH_Type_L1B:EV_1KM_RefSB
图2 使用gdalinfo查看子数据集的输出信息

由于输出的信息太多,截图不能全部显示,就意思一下,这里就不在贴出来了。有了上面的试验,接下来我们就可以写程序来读取HDF数据了,首先是用gdal打开hdf数据,获取Subdatasets中的子数据集路径,然后再使用gdalopen来打开。至于这个Subdatasets其实就在gdal的元数据里面,可以使用函数,GDALDataset::GetMetadata()函数来获取。示例代码如下:

 GDALAllRegister();const char* pszSrcFile = "F:\\Data\\HDF\\MOD021KM.A2010287.0250.005.2010287121743.hdf";GDALDataset *pDataSet = (GDALDataset *) GDALOpen( pszSrcFile, GA_ReadOnly );if (pDataSet == NULL){printf("不能打开该文件,请检查文件是否存在!");return RE_FILENOTEXIST;}char ** papszSUBDATASETS = GDALGetMetadata( (GDALDatasetH)pDataSet, "SUBDATASETS");

这段代码最后一行的papszSUBDATASETS中就是存储的子数据的路径和描述信息。papszSUBDATASETS其实就是个字符串数组,接下来就是解析这个字符串数组,然后从里面获取HDF子数据集的路径和描述信息,这里需要注意的是,如果一个HDF文件获取的子数据集是NULL,也就是papszSUBDATASETS这个变量如果为NULL,说明这个hdf数据本身就是一个单一的数据,里面没有子数据集。接下来的代码就是解析这个子数据集的字符串数组:

 vector<string> vSubDataSets, vector<string> vSubDataDesc;if ( papszSUBDATASETS == NULL ){string papszMetadata = GDALGetDriverShortName((GDALDriverH)pDataSet);vSubDataSets.push_back(papszMetadata);vSubDataDesc.push_back(papszMetadata);}

上面的代码中是如果当前的HDF数据没有子数据集,那么其本身就是一个数据集。这里定义了两个vector<string>,分别用来存储子数据集的路径和描述信息。下面的代码就是解析含有子数据集的HDF数据了。这里需要一点点的std::string的函数,主要是用来截取字符串用的substr函数。

 else{int iCount = CSLCount(papszSUBDATASETS);if(  iCount <= 0 ){if(pProcess != NULL)pProcess->SetMessage("该HDF文件中没有子数据!");GDALClose((GDALDriverH)pDataSet);return RE_SUCCESS;}for(int i=0; papszSUBDATASETS[i] != NULL; i++ ){if(i%2 != 0)continue;string tmpstr = string(papszSUBDATASETS[i]);tmpstr = tmpstr.substr(tmpstr.find_first_of("=") + 1);const char *tmpc_str = tmpstr.c_str();string tmpdsc = string(papszSUBDATASETS[i+1]);tmpdsc = tmpdsc.substr(tmpdsc.find_first_of("=") + 1);GDALDatasetH hTmpDt = GDALOpen(tmpc_str, GA_ReadOnly);if(hTmpDt != NULL){vSubDataSets.push_back(tmpstr);vSubDataDesc.push_back(tmpdsc);GDALClose(hTmpDt);}}//end for}GDALClose((GDALDriverH)pDataSet);

对上面的代码稍微解释一下:首先使用CSLCount函数获取这个字符串数组的个数,如果不大于0就说明没有,直接关闭HDF数据返回。如果大于0,遍历这个字符串数组,一般这个字符串数组个数肯定是个偶数,你也可以提前判断一下。如果数组的下标是奇数,直接跳过,也就是说,我们直接取下标是0、2、4的字符串。接下来取出的字符串中是有一个“=”连接起来的(具体可以看上面的例子)。这个等号的左边是描述数据集的顺序,右边是值也就是子数据集的路径。使用substr函数把路径取出来存储到前面定义的vector<string>中,同时获取描述信息也存进去(这个描述信息可以不用,如果需要用户交互的话还是留着的好),接下来使用GDALOpen打开测试一下这个子数据集的路径是否正确,如果可以打开就说明正常。

通过上面的说明,对于HDF的数据(包括HDF4、HDF5、NetCDF等类型的数据)怎么使用GDAL打开就有个了解了吧。下面是我写的一个简单的Demo截图,核心功能就是用的上面这段代码。
首先是打开HDF数据,如图3所示:

图3 打开HDF数据

点击打开之后会弹出一个对话框,如图4所示,会在列表中显示打开的HDF数据中所有的子数据集的描述信息,通过用户选择来指定所要打开的子数据集,这个对话框中的列表显示的内容就是上面代码中解析的描述信息。然后点击确定的时候通过选择的第几个来定位子数据集的路径,然后使用GDAL打开进行显示或者进行其他的处理即可。

图4 打开HDF数据后列举的子数据集描述

使用GDAL获取HDF等数据集中的图像相关推荐

  1. python 转换深度摄像头获取的字节流数据为16bitPNG图像

    import numpy as np import struct import matplotlib.pyplot as pltfile = open(r"二进制文件目录", &q ...

  2. 【C++】GDAL读取HDF数据

    (45条消息) VS2019c++配置GDAL和HDF库新手入门_程程gg酱的博客-CSDN博客_gdal vs2019 (45条消息) 使用GDAL获取HDF等数据集中的图像_箜_Kong的博客-C ...

  3. 使用GDAL对HDF数据进行校正

    在使用HDF的数据时,首先要对其进行校正处理.比如MODIS数据中,有个去除蝴蝶结现象.一般出现这种情况会在低分辨率卫星数据中(个人理解),比如气象卫星,海洋卫星等,这类数据一般的数据分辨率都很低,几 ...

  4. 使用GDAL对静止卫星圆盘数据进行校正(以FY2为例子)

    前言 使用GDAL对静止卫星数据的校正的方式与之前写的校正MODIS数据一样,只不过对于静止卫星的圆盘数据而言,经纬度查找是固定的,不会发生变化. 经纬度查找表数据 对于FY2气象卫星而言,经纬度查找 ...

  5. lsdyna如何设置set中的node_list_如何使用Python处理HDF格式数据

    HDF也是一种自描述格式文件,主要用于存储和分发科学数据.气象领域中卫星数据经常使用此格式,比如MODIS,OMI,LIS/OTD等卫星产品.对HDF格式细节感兴趣的可以Google了解一下. 这一次 ...

  6. python gdal:hdf转tif

    比较多的人用arcpy转换hdf文件(https://blog.csdn.net/Orange_GISer/article/details/122978951?spm=1001.2101.3001.6 ...

  7. 使用Geolocation校正GDAL不支持的数据

    对于低分数据来说,常用的校正方式就是给定数据的经纬度查找表来进行校正.在GDAL中,这种校正方式叫Geolocation array.常用的数据有国外的MODIS数据,国内的如风云系列(FY)和海洋系 ...

  8. GDAL读取S-57海图数据中文属性值乱码问题解决

    使用GDAL读取S-57海图数据时,对于属性表中的中文属性值读出来是乱码.如图1所示. 图1 S57海图数据中文乱码字段 通过调试代码发现,S-57文件中的中文是按照宽字节存储在文件中,而GDAL在读 ...

  9. 使用GDAL工具对OrbView-3数据进行正射校正

    本文原文地址:http://gis-lab.info/qa/orbview3-ortho-gdal.html,借助于Google Translate工具翻译整理了一下.下文中的命令行截图是我本机测试的 ...

最新文章

  1. Web 开发与设计之 Google 兵器谱
  2. is 和 ==的区别
  3. 管中窥豹,初探Win RE(Windows恢复环境)
  4. ES6 继承(复习原型链继承)
  5. RTC是DS1339,驱动采用的是rtc-ds1307.c
  6. 验算双中心重叠积分程序
  7. 几种替代MATLAB的工具,堪称完美!
  8. 互联网医院 2020年突出成就_资讯丨2020中国医院互联网影响力排行榜
  9. 我就是我,不一样的browser
  10. mysql大数据量处理
  11. Java生鲜电商平台-高并发核心技术订单与库存实战
  12. python 合并excel 自动更新_手把手教你4种方法用Python批量实现多Excel多Sheet合并
  13. WINCE6.0 DM.EXE 激活驱动失败的原因之一
  14. wxpython实现简单图书管理系统
  15. PS使用:windows解决Adobe Photoshop 2020(PS2020)闪退
  16. 记一次Maya使用入门
  17. android如何释放图片缓存
  18. [华为 HCNA ] VLAN的介绍和划分
  19. iOS 直播类,交友类,陪玩类 app 上架攻略
  20. 网络工程师加入德云社说相声,他还骑摩托车环球旅行!!

热门文章

  1. vue中watch监听路由传来的参数变化
  2. 变量案例弹出用户名(JS)
  3. 2D转换中心点transform-origin(CSS3)
  4. java字面量和符号引用_JVM中的直接引用和符号引用
  5. 过去一年,被我们“高估”的技术清单
  6. odoo开发笔记 -- 翻译机制及导入.po文件
  7. spring源码解析bean定义五ContextNamespaceHandler一
  8. ruby 数据类型Symbol
  9. Android逆向从入门到入土(smali修改,so修改)
  10. Requirejs常用配置和应用