GDAL 数据模型
目录
GDAL 数据模型
2012年1月19日
1 概述
GDAL:geospatial dataabstraction library(地理数据抽象库)。
用于将各种栅格数据转换为统一的抽象格式。
OGR:OpenGIS SimpleFeatures Reference Implementation(开源GIS简单元素参考实现)。
用于将各种矢量数据转换为统一的抽象格式。
CPL:common portabilitylibrary。通用可移植库。
用于针对不同OS声明的通用定义。
GDAL按照波段为操作单位,每个波段操作完成后再操作其它波段。
参考:http://www.baike.com/wiki/CPL
2 api
2.1 CPL
CSLFetchBoolean():获取CPL String List中的属性值boolean。
CSLSetNameValue():设置键值对。
CPLMalloc():申请内存。
2.1.1GDALProgressFunc:进度回调函数。
定义:
int (CPL_STDCALL *GDALProgressFunc)(double dfComplete,const char *pszMessage, void *pProgressArg);
dfComplete:表示当前完成的进度(0~1之间的小数)。
pszMessage:字符串消息,通常为NULL。
pProgressArg:由CreateCopy传递过来的参数。
返回值:TRUE/FALSE返回当前状态,如果需要终止当前操作,则返回FALSE,程序中断,返回TRUE,正常执行。
2.2 GDAL
GDALAllRegister():加载所有驱动。
GDALOpen():打开数据集。打开方式有GA_READONLY/GA_UPDATE。
GDALClose():关闭数据集。
GDALGetRasterDataTypeName():返回枚举值表示的像素大小。
GDALGetColorInterpretationName():返回枚举值表示的颜色类型。
GDALComputeRasterMinMax():计算当前图像波段像素值的最大值、最小值。
GDALReadBlock():读取波段内的块数据。
GetGDALDriverManager():获取GDALDriverManager类的单例。
2.3 WARP
用于高效的图形变换,以及大数据操作。包含一组重采样方法及一组Mask方法(GDALTransformerFunc函数族)。
使用方法:
使用GDALWarpOptions类设置操作的相关参数。
使用GDALWarpOperation类执行变换操作(需要使用GDALWarpOptions作为参数)。
2.3.1 GDALWarpOptions
hSrcDS:源数据集。
hDstDS:目标数据集。
nBandCount:波段数。
panSrcBand/panDstBand:源数据集、目标数据集波段排列。必须使用CPLMalloc在DLL内部申请(因为后面要调用GDALDestroyWarpOptions()的时候要释放,如果使用了外部内存,会出现错误)。如:(int*)CPLMalloc(sizeof(int)*3)
pfnProcess:进度回调函数指针。参见2.1.1。
pTransformerArg:为转换函数pFuncTransformer准备参数。需要一组参数列表。使用GDALCreateGenImgProjTransformer(),GDALCreateReprojectionTransformer(),GDALCreateGCPTransformer(),GDALCreateApproxTransformer()可以创建参数。
pFuncTransformer:转换函数指针。用于将输入和输出进行转换。这是图形变换的主要功能。有部分预定义函数可供使用,也可以自己定义。声明类型为
typedef int(*GDALTransformerFunc)( void *pTransformerArg,
int bDstToSrc, intnPointCount,
double *x, double *y,double *z, int *panSuccess );
2.3.2 GDALCreateGenImgProjTransformer()和GDALGenImgProjTransform()
创建GeneralImage Project Transform参数。为函数GDALGenImgProjTransform()的函数列表。
GDALGenImgProjTransform():用于进行源图像和目标图像之间的投影变换。变换过程为:Image图像转换为带有源坐标系统的Map,将Map的源坐标系统转换为目标目标系统,将目标坐标系统转换为目标图像。
在转换为的过程中,使用坐标系统,使用GeoTransform()6参数,如果没有,则使用GCP。
void*GDALCreateGenImgProjTransformer ( GDALDatasetH hSrcDS,
const char * pszSrcWKT,
GDALDatasetH hDstDS,
const char * pszDstWKT,
int bGCPUseOK,//TRUE:use gcp if no wkt
double dfGCPErrorThreshold,//ErrorThreshhold
int nOrder //GCP maxmum order
)
2.3.3 GDALWarpOperation
用于执行变换。
Initialize():加载参数。
ChunkAndWarpImage():变换函数。
ChunkAndWarpMulti():多线程变换。
2.4 OGR
2.5 SpatialReference
2.6 DriverImplement
3 数据集GDALDataset
GDAL数据集,表示栅格图像的集合,通常是一个图像文件(及其相同的文件)。
3.1 成员函数
GDALDataset::GetGeoTransform():获取坐标转换参数(与worldfile文件格式相同,参见:..\..\GIS\worldfile.docx)。
GetRasterBand(index):获取影像波段。index的基数是1。
GetRasterCount():波段数。
GetRasterXSize()/GetRasterYSize():x和y方法像素数目。
GetProjectionRef():Proj格式的投影信息。
GetGeoTransform():获取仿射变换的参数。
3.1.1 RasterIO
3.1.1.1 定义
CPLErr GDALDataset::RasterIO |
( |
eRWFlag, |
|
int |
nXOff, |
||
int |
nYOff, |
||
int |
nXSize, |
||
int |
nYSize, |
||
void * |
pData, |
||
int |
nBufXSize, |
||
int |
nBufYSize, |
||
eBufType, |
|||
int |
nBandCount, |
||
int * |
panBandMap, |
||
int |
nPixelSpace, |
||
int |
nLineSpace, |
||
int |
nBandSpace |
|
|
) |
RasterIO(RWFlage,left,top,width,height,pBuf,dstWidth,dstHeight,type,bandCount,pixelSpace,lineSpace,bandSpace):操作Raster。可以同时操作多个波段。
eRWFlag:读写标志
nXOff:左上角X(读取图像的X起点)
nYOff:左上角Y(读取图像的Y起点)
nXSize:读取宽度
nYSize:读取高度
pData:返回的BUF(因为为从0,0开始,所以与nXoff,nYOff对应的参数为0,0省略)
nBufXSize:buf的宽度(如果与原始图像不同,也就缩放,则会抽取或复制图像像素)
nBufYSize:buf的高度(如果与原始图像不同,也就缩放,则会抽取或复制图像像素)
eBufType:读取的每个波段的每个像素(像素的子波段)的宽度(单位:字节)。
nBandCount:读取的波段数
panBandMap:buf的每个像素中波段的排列顺序。
nPixelSpace:buf中每个像素的宽度(每个像素的总大小=各波段像素的和)(单位:字节)
nLineSpace:buf中每行的大小(单位:字节)。
nBandSpace:buf中下一个波段的像素与上一个波段的像素之间间隔(单位:字节)。
3.1.1.2 参考
gdalAPI。
http://blog.csdn.net/liminlu0314/article/details/7072224
3.1.1.3 示例
#include<gdal_priv.h>
#include<cpl_conv.h>
#pragmacomment(lib,“gdal_i.lib”)
voidCioDlg::OnBnClickedButton1()
{
// TODO:
在此添加控件通知处理程序代码
GDALDataset*pDs=NULL;
GDALAllRegister();
pDs=(GDALDataset*)GDALOpen(“D:\\output\\out\\J50D001001_lonlat-L15.tif”,GA_ReadOnly);
{//read all bytes
intiXSize,iYSize;
iXSize=pDs->GetRasterXSize();
iYSize=pDs->GetRasterYSize();
intRGB[]={1,2,3};
char*pBufLine=(char*)CPLMalloc(sizeof(char)*iXSize*3*2);//缓冲一行,申请两行的内存(做实验,可能会用到较多内存
pDs->RasterIO(GF_Read,0,0,iXSize,1,pBufLine,iXSize,1,GDT_Byte,3,RGB,(GDT_Byte)*3,(GDT_Byte)*3*iXSize,1);//读原始数据,第一行
memset(pBufLine,0x00,sizeof(char)*iXSize*3*2);
pDs->RasterIO(GF_Read,1,0,iXSize–1,1,pBufLine,iXSize–1,1,GDT_Byte,3,RGB,(GDT_Byte)*3,((GDT_Byte)*3*iXSize–1),1);//读原始数据,第一行第一列至第一行结束
memset(pBufLine,0x00,sizeof(char)*iXSize*3*2);
pDs->RasterIO(GF_Read,0,0,iXSize,1,pBufLine,iXSize,1,GDT_Byte,3,RGB,(GDT_Byte)*3,(GDT_Byte)*3*iXSize,2);//读原始数据,第一行,波段间隔2,导致数据间隔2填充,如RGBRGB-》R00R00-》R0GR0G-》R0GRBG…
memset(pBufLine,0x00,sizeof(char)*iXSize*3*2);
pDs->RasterIO(GF_Read,0,0,iXSize,1,pBufLine,iXSize,1,GDT_Byte,3,RGB,(GDT_Byte)*3,(GDT_Byte)*3*iXSize,3);//读原始数据,第一行,波段间隔3,导致数据间隔3填充,如RGBRGB-》R00R00R00-》R00G00G00-》R00G00B00…
TRACE(“OK”);
}
GDALClose((GDALDatasetH)pDs);
}
4 波段GDALRasterBand
数据波段,用于表示数据集中一个通道。
GetBlockSize(x,y):获取管理文件的单位块大小。对于不同的文件格式,有不同的大小。一般为一行的大小(x=width,y=1),而瓦片则是整个瓦片的大小。也有一些会被分割成不同的大小。
GetRasterDataType():获取像素数据类型。返回以GDT_xxx表示的枚举值。表示每个像素的大小。
GetColorInterpretation():获取颜色表类型。返回以GCI_xxx表示的枚举值。表示颜色对应的颜色表。
GetMinimum()、GetMaxmum():计算最小值、最大值,如果文件中不包含相关信息,则返回像素类型的最小值、最大值。
ComputeRasterMinMax():计算当前图像波段的最大值,最小值。
RasterIO(RWFlage,xleft,ytop,xRead,yRead,pbuf,xBuf,yBuf,type,pixelspace,linespace):读写IO。
5 坐标系统
坐标系统使用WKT格式。
有两种定义方式(AffineGeoTransform和GCP),可以不定义,但不能同时定义(因无法指定使用哪一个)。
GetProjectionRef():返回由AffineGeotransform(GetGeoTransform())定义的坐标系统。
GetGCPProjection():返回由GCP(GetGCPs())定义的坐标系统。
5.1 AffineGeoTransform仿射参数
由二元仿射变换参数指定。与Worldfile6(..\..\GIS\worldfile.docx)参数相同。
5.2 GCP控制点参数
控制点参数定义为:
typedef struct
{
char *pszId; //控制点ID
char *pszInfo;//附加信息,通常为NULL
double dfGCPPixel;//像素X
double dfGCPLine;//像素Y
double dfGCPX;//空间X
double dfGCPY;//空间Y
double dfGCPZ;//空间Z,通常为0
} GDAL_GCP;
6 元数据MetaData
一系列键值对。可以分为不同的Domain。
7 ColorTable颜色表和调色板
颜色表定义了各个波段的可能用到的颜色通道。
调用板定义了不同的颜色方案。
8 Overview缩略图
用于快速显示的抽稀图。
9 GDALDriverManager
GDAL支持的Raster格式驱动类。
用于管理所有的驱动。
单例。
使用GetGDALDriverManager()获取单例。
GetDriverByName():按照名称获取驱动。
10 格式驱动GDALDriver
Raster格式的驱动类实现。
用于管理Dataset。
Create/Delete/Rename::创建、删除、重命名Dataset。
CopyFiles():复制Dataset文件。
CreateCopy():复制Dataset到文件。默认使用Create()。可以添加回调函数返回当前的进度。需要参数从源数据集中取。
Create():有可能不支持。需指定必须参数:width,height,bandcount。
QuietDelete():删除。
GetMetaData():获取属性的键值对。
11 操作
11.1 读取图像为RGB
void CioDlg::OnBnClickedButton1()
{
// TODO: 在此添加控件通知处理程序代码
GDALDataset *pDs =NULL;
GDALAllRegister();
pDs = (GDALDataset*)GDALOpen(“D:\\output\\out\\J50D001001_lonlat-L15.tif”,GA_ReadOnly);
{//read all bytes
intiXSize,iYSize;
iXSize =pDs->GetRasterXSize();
iYSize =pDs->GetRasterYSize();
intRGB[]={1,2,3};
char*pBufLine = (char *) CPLMalloc(sizeof(char)*iXSize*3*2);//缓冲一行,申请两行的内存(做实验,可能会用到较多内存
pDs->RasterIO(GF_Read,0,0,iXSize,1,pBufLine,iXSize,1,GDT_Byte,3,RGB,(GDT_Byte)*3,(GDT_Byte)*3*iXSize,1);//读原始数据,第一行
TRACE(“OK”);
}
GDALClose((GDALDatasetH)pDs);
}
11.2 创建文件
文件创建由Driver支持,一般有两种,CreateCopy():全部支持。Create():部分支持。
CreateCopy:由已经存在的Dataset复制到指定的文件。(需要的参数从源数据集中取)
Create():创建文件。必须指定大小和波段数。
//int (CPL_STDCALL *GDALProgressFunc)(double dfComplete, const char*pszMessage, void *pProgressArg);
int CPL_STDCALL pProcFun(double dfComplete, const char *pszMessage, void *pProgressArg)
{
TRACE(“Process:%f%%,%s,%d\n”,dfComplete*100,pszMessage,(int)pProgressArg);
return 1;
}
void createFile(void)
{
GDALAllRegister();
GDALDataset *pDs =(GDALDataset*)GDALOpen(“D:\\output\\out\\J50D001001_lonlat-L15.tif”,GA_ReadOnly);
GDALDriverManager*pManager = GetGDALDriverManager();
GDALDriver *pDriver =pManager->GetDriverByName(“GTiff”);
char **pMetaData =pDriver->GetMetadata();
{
int iTrue= CSLFetchBoolean(pMetaData,GDAL_DCAP_CREATECOPY,FALSE);
TRACE(“CreateCopy=%d\n”,iTrue);
}
{
int iTrue= CSLFetchBoolean(pMetaData,GDAL_DCAP_CREATE,FALSE);
TRACE(“Create=%d\n”,iTrue);
}
char **pOption = NULL;
pOption =CSLSetNameValue(pOption,”TILED”,”YES”);
pOption =CSLSetNameValue(pOption,”COMPRESS”,”PACKBITS”);
//{
// GDALDataset *pDsDst =pDriver->CreateCopy(“D:\\output\\out\\J50D001001_lonlat-L15xxxx.tif”,pDs,FALSE,pOption,pProcFun,(void*)7);
// GDALClose(pDsDst);
//}
{
GDALDataset*pDsDst =pDriver->Create(“D:\\output\\out\\J50D001001_lonlat-little.tif”,512,512,1,GDT_Byte,NULL);
doublepAffine[6];
pDs->GetGeoTransform(pAffine);
pDsDst->SetGeoTransform(pAffine);
pDsDst->SetProjection(pDs->GetProjectionRef());
charpBuf[512*512];
memset(pBuf,0x7d,512*512*1);
pDsDst->GetRasterBand(1)->RasterIO(GF_Write,0,0,512,512,pBuf,512,512,GDT_Byte,0,0);
GDALClose(pDsDst);
}
GDALClose((GDALDatasetH)pDs);
}
11.3 RGB输出为文件
#include <gdal_priv.h>
#include <cpl_conv.h>
#pragma comment(lib,”gdal_i.lib”)
//int (CPL_STDCALL *GDALProgressFunc)(double dfComplete, const char*pszMessage, void *pProgressArg);
int CPL_STDCALL pProcFun(double dfComplete, const char *pszMessage, void*pProgressArg)
{
TRACE(“Process:%f%%,%s,%d\n”,dfComplete*100,pszMessage,(int)pProgressArg);
return 1;
}
void createFile(void)
{
GDALAllRegister();
GDALDataset *pDs =(GDALDataset*)GDALOpen(“D:\\output\\out\\J50D001001_lonlat-L15.tif”,GA_ReadOnly);
GDALDriverManager*pManager = GetGDALDriverManager();
GDALDriver *pDriver =pManager->GetDriverByName(“GTiff”);
char **pMetaData = pDriver->GetMetadata();
{
int iTrue= CSLFetchBoolean(pMetaData,GDAL_DCAP_CREATECOPY,FALSE);
TRACE(“CreateCopy=%d\n”,iTrue);
}
{
int iTrue= CSLFetchBoolean(pMetaData,GDAL_DCAP_CREATE,FALSE);
TRACE(“Create=%d\n”,iTrue);
}
char **pOption = NULL;
pOption =CSLSetNameValue(pOption,”TILED”,”YES”);
pOption =CSLSetNameValue(pOption,”COMPRESS”,”PACKBITS”);
//{copy dataset to file
// GDALDataset *pDsDst =pDriver->CreateCopy(“D:\\output\\out\\J50D001001_lonlat-L15xxxx.tif”,pDs,FALSE,pOption,pProcFun,(void*)7);
// GDALClose(pDsDst);
//}
//{//rgb 2 file by band
// GDALDataset *pDsDst =pDriver->Create(“D:\\output\\out\\J50D001001_lonlat-little.tif”,512,512,3,GDT_Byte,NULL);
// double pAffine[6];
// pDs->GetGeoTransform(pAffine);
// pDsDst->SetGeoTransform(pAffine);
// pDsDst->SetProjection(pDs->GetProjectionRef());
// char pBuf[512*512];
// memset(pBuf,0x7d,512*512*1);
// pDsDst->GetRasterBand(1)->RasterIO(GF_Write,0,0,512,512,pBuf,512,512,GDT_Byte,0,0);
// memset(pBuf,0x00,512*512*1);
// pDsDst->GetRasterBand(2)->RasterIO(GF_Write,0,0,512,512,pBuf,512,512,GDT_Byte,0,0);
// memset(pBuf,0xFF,512*512*1);
// pDsDst->GetRasterBand(3)->RasterIO(GF_Write,0,0,512,512,pBuf,512,512,GDT_Byte,0,0);
// GDALClose(pDsDst);
//}
{//rgb 2 file entirely
GDALDataset*pDsDst =pDriver->Create(“D:\\output\\out\\J1.tif”,512,512,3,GDT_Byte,NULL);
doublepAffine[6];
pDs->GetGeoTransform(pAffine);
//pAffine[0]+= 0.02197265625;
//pAffine[3]-= 0.02197265625;
pDsDst->SetGeoTransform(pAffine);
pDsDst->SetProjection(pDs->GetProjectionRef());
charpBuf[512*512*3];
for(int i= 0;i<512;i++)
{
for(intj = 0;j<512;j++)
{
memset(pBuf+i*3*512+j*3+0,0×12,sizeof(char));
memset(pBuf+i*3*512+j*3+1,0×52,sizeof(char));
memset(pBuf+i*3*512+j*3+2,0×52,sizeof(char));
}
}
intpanBand[] = {1,2,3};
pDsDst->RasterIO(GF_Write,0,0,512,512,pBuf,512,512,GDT_Byte,3,panBand,3*sizeof(char),3*512*sizeof(char),sizeof(char));
GDALClose(pDsDst);
}
GDALClose((GDALDatasetH)pDs);
}
11.4 图幅拼接
void combineImage(void)
{
GDALAllRegister();
GDALDriverManager*pManager = GetGDALDriverManager();
GDALDriver *pDriver =pManager->GetDriverByName(“GTiff”);
GDALDataset *pDsDst =pDriver->Create(“D:\\output\\dst-combine.tif”,512*2,512*2,3,GDT_Byte,NULL);
//get image 1 rgb
GDALDataset *pDs =NULL;
pDs = (GDALDataset*)GDALOpen(“D:\\output\\J1.tif”,GA_ReadOnly);
GDALDataset *pDs2 =NULL;
pDs2 = (GDALDataset*)GDALOpen(“D:\\output\\J2.tif”,GA_ReadOnly);
for(int iBand =1;iBand<=3;iBand++)
{
charpBuf[512*512];
{//read
memset(pBuf,0x00,512*512*1);
pDs->GetRasterBand(iBand)->RasterIO(GF_Read,0,0,512,512,pBuf,512,512,GDT_Byte,0,0);
}
//getimage 2 rgb
charpBuf2[512*512];
{//read
memset(pBuf2,0x00,512*512*1);
pDs2->GetRasterBand(iBand)->RasterIO(GF_Read,0,0,512,512,pBuf2,512,512,GDT_Byte,0,0);
}
//write
for(inti = 0;i<512;i++)
{
pDsDst->GetRasterBand(iBand)->RasterIO(GF_Write,0,i,512,1,pBuf+512*i,512,1,GDT_Byte,0,0);
pDsDst->GetRasterBand(iBand)->RasterIO(GF_Write,512,i,512,1,pBuf2+512*i,512,1,GDT_Byte,0,0);
}
}
}
11.5 重采样
#include<gdalwarper.h>
voidwarpImage(void)//resample
{
GDALAllRegister();
GDALDataset *pSrcDS = (GDALDataset*)GDALOpen(“D:\\output\\J1.tif”,GA_ReadOnly);
GDALDataset *pDstDS = pSrcDS->GetDriver()->Create(“D:\\output\\warp_dst.tif”,pSrcDS->GetRasterXSize()/2,pSrcDS->GetRasterYSize()/2,
pSrcDS->GetRasterCount(),pSrcDS->GetRasterBand(1)->GetRasterDataType(),NULL);
{//affine
double dAffine[6];
pSrcDS->GetGeoTransform(dAffine);
pDstDS->SetGeoTransform(dAffine);
}
pDstDS->SetProjection(pSrcDS->GetProjectionRef());
GDALWarpOptions *pOptions =GDALCreateWarpOptions();
pOptions->hSrcDS =(GDALDatasetH)pSrcDS;
pOptions->hDstDS =(GDALDatasetH)pDstDS;
pOptions->eResampleAlg =GRA_Bilinear;
pOptions->nBandCount = 3;
int panBandMap[] = {1,2,3};
pOptions->panSrcBands = (int *)CPLMalloc(sizeof(int) * 3 );
pOptions->panSrcBands[0] = 1;
pOptions->panSrcBands[1] = 2;
pOptions->panSrcBands[2] = 3;
pOptions->panDstBands = (int *)CPLMalloc(sizeof(int) * 3 );
pOptions->panDstBands[0] = 1;
pOptions->panDstBands[1] = 2;
pOptions->panDstBands[2] = 3;
pOptions->pfnProgress =pProcFun;
pOptions->pTransformerArg =GDALCreateGenImgProjTransformer(pOptions->hSrcDS,GDALGetProjectionRef(pOptions->hSrcDS),pOptions->hDstDS,GDALGetProjectionRef(pOptions->hSrcDS),FALSE,0.0,1);
pOptions->pfnTransformer =GDALGenImgProjTransform;
GDALWarpOperation pOperate;
pOperate.Initialize(pOptions);
pOperate.ChunkAndWarpImage(0,0,pDstDS->GetRasterXSize(),pDstDS->GetRasterYSize());
GDALDestroyGenImgProjTransformer(pOptions->pTransformerArg);
GDALDestroyWarpOptions(pOptions);
GDALClose(pSrcDS);
GDALClose(pDstDS);
}
转载自:https://blog.csdn.net/sf2gis2/article/details/50686742