Wechat: yu389741| Email: gisdqy@163.com

Shop:https://www.giserdqy.com/shop

第一个GDAL代码实践


刚刚开始学习GDAL,在http://blog.csdn.net/liminlu0314/article/details/7072007的参考下写了第一个小代码:

// GDAL_1.cpp : 定义控制台应用程序的入口点。
//

#include "stdafx.h"
#include "gdal_priv.h"
#include "cpl_conv.h"
#include<iostream>
#include<string>

int _tmain(int argc, _TCHAR* argv[])
{
	//注册文件格式;
	GDALAllRegister();
	const char* pszFile= "psb.jpg";

	GDALDataset* pDataset = (GDALDataset*)GDALOpen(pszFile,GA_ReadOnly);

	if(NULL==pDataset)
	{
		std::cout<<"File doesn't exist!"<<std::endl;
		return 0;
	}
	//输出图像格式信息:
	//输出文件格式信息,首先获得Driver驱动指针?
	CPLString strDrive = pDataset->GetDriver()->GetDescription();
	CPLString strInfo = pDataset->GetDriver()->GetMetadataItem(GDAL_DMD_LONGNAME);
	std::cout<<"文件格式:"<<strDrive<<"  "<<strInfo<<std::endl;

	//输出文件大小;
	int i = pDataset->GetRasterXSize();
	int j = pDataset->GetRasterYSize();
	int k = pDataset->GetRasterCount();
	std::cout<<"影像宽:"<<i<<std::endl;
	std::cout<<"影像高:"<<j<<std::endl;
	std::cout<<"影像波段数:"<<k<<std::endl;

	//输出文件投影方式:
	CPLString strProjection = pDataset->GetProjectionRef();
	if(strProjection!="")                         //这里如果没有投影信息,返回一个空字符串;不是NULL;
	{
		//printf( "Projectionis `%s'\n", pDataset->GetProjectionRef());
		std::cout<<"投影方式:"<<strProjection<<std::endl;
	}
	
	//输出图像的坐标和分辨率信息;
	double GeoTransform[6];
	if(pDataset->GetGeoTransform(GeoTransform)==CE_None)       //CE_None表示成功获取设置的仿射变换参数
	{                                                         //默认的六个参数是0,1,0,0,0,1
		for(i=0;i<6;i++)
		{
			std::cout<<GeoTransform[i]<<"  ";
		}
		std::cout<<std::endl;
	}

	//图像波段信息;
	GDALRasterBand* poRasterBand;
	poRasterBand = pDataset->GetRasterBand(1);    //第一个波段的指针;
	int nxBlock,nyBlock;
	poRasterBand->GetBlockSize(&nxBlock,&nyBlock);
	CPLString DataType =GDALGetDataTypeName(poRasterBand->GetRasterDataType());                    //获取数据类型名字;
	CPLString ColorType = GDALGetColorInterpretationName(poRasterBand->GetColorInterpretation());  //获取颜色类型名称;
	std::cout<<"分块大小为:"<<nxBlock<<"×"<<nyBlock<<DataType<<std::endl;
	std::cout<<"颜色类型为:"<<ColorType<<std::endl;

	//统计像素的最大值最小值;
	int ArrMaxMin[2];
	ArrMaxMin[0] = poRasterBand->GetMaximum();
	ArrMaxMin[1] = poRasterBand->GetMinimum();
	std::cout<<"像素数据的最值为:"<<ArrMaxMin[0]<<"和"<<ArrMaxMin[1]<<std::endl;

	//输出图像的金字塔信息
	if(poRasterBand->GetOverviewCount()!=0)         //该函数获得当前波段的金字塔层数,如果没有金字塔返回0;
	{
		std::cout<<"金字塔数目为:"<<poRasterBand->GetOverviewCount()<<std::endl;
	}

	//输出图像的颜色表信息:
	if(poRasterBand->GetColorTable()!=NULL)
	{
		std::cout<<"颜色表信息:"<<poRasterBand->GetColorTable()->GetColorEntryCount()<<std::endl;
	}

	//读取图像数据:
	int nXsize = poRasterBand->GetXSize();
	int nYsize = poRasterBand->GetYSize();
	char *pBuf = new char[sizeof(GDT_Byte)*nXsize];
	poRasterBand->RasterIO(GF_Read,0,0,nXsize,1,pBuf,nXsize,1,GDT_Byte,0,0);
	delete[] pBuf;

	std::cin.get();
	std::cin.get();
	return 0;
}

1:首先介绍一下代码中出现的几个类:

GDALDataSet一套关联栅格波段,通常来自一个文件。数据成员包括GDALDriver指针,波段的数目大小,波段列表,引用计数,是否被共享。等信息。以及一GDALDefaultOverViews对象。提供一个IRasterIO接口给派生类使用,作为读取数据的接口。派生于GDALMajorObject类,该类是GDAL所有类的父类;

核心类 GDALMajorObject,它定义了一些操作元数据的属性和方法供子类继承。元数据:data about date 描述数据的数据,majorobject使用GDALMultiDomainMetadata

对象存储元数据。该对象存在一个域名列表和一个元数据内容列表。用户传入域名以及元数据内容已进行数据设置。可序列化为xml。

GDALDriver数据驱动类,只定义了成员方法,没有成员变量,通过函数指针来实现对于不同的驱动类型采用不同的方式。有Create方法创建数据集,Delete删除数据集,

Rename重命名数据集,CopyFile,CreateCopy另外定义了其他函数指针,算是接口了。在注册的时候,根据对象类型创建driver,并设置driver的描述,元数据等,并设置函

数指针为对应数据集的静态函数。如poDriver->pfnOpen = JDEMDataset::Open。其中Open方法为JDEMDataset中的静态函数。

GDALRasterBand;一个单一的栅格数据波段类,存在一个GDALRasterBlock友元存在一个GDALDataset对象(GDAL貌似很喜欢把外层对象的指针存在分类的对象里面。

如在学生的信息里面存储班级的信息,班级的信息里面要有一个年级的指针,当然,班级类是学生类的友元,年级类是班级类的友元。难道是学生犯错了,然后由班级处置的

意思?)Rasterband中定义了比rasterdataset更细致的数据类型。

2:函数介绍:

Virtual GDALDriver * GetDriver(void); 取得dataset有关系的驱动;获得当前数据集的驱动格式,返回当前数据集的驱动指针;

Int GetRasterXSize(void);取出栅格宽度,单位像素;

Int GetRasterYSize();取得栅格高度,单位像素

Int GetRasterCount();取得该dataset中栅格波段数目

Virtual const char *GetProjectionRef(void);取得该dataset的投影定义字符

Virtual CPLErr GetGeoTransform (double *); 取得仿射投影变换系数,返回值为CPL_Err类型;关于该类型:

typedef enum
{
    CE_None = 0,
    CE_Debug = 1,
    CE_Warning = 2,
    CE_Failure = 3,
    CE_Fatal = 4
} CPLErr;

其实就是一个包含五个数据的枚举类型;
void GetBlockSize(int* pnXsize,int* pnYsize);获得数据默认的分块大小;pnXsize和pnYsize分别表示分块的X和Y大小;

Virtual GDALColorTable* GDALRasterBand::GetColorTable();获得当前波段的颜色表信息,返回颜色表指针;

Virtual int GDALRasterBand::GetOverviewCount();获得当前波段的金字塔层数,如果没有金字塔返回0;

运行结果:

转载自:https://blog.csdn.net/zhang_alongzd/article/details/51527360