GDAL分塊處理簡單的流程
阿新 • • 發佈:2018-11-03
GDAL分塊處理簡單的流程
GDAL分塊處理流程
使用GDAL庫在編寫影象處理演算法時,為了提高處理的效率,經常會進行分塊處理,下面的程式碼是使用GDAL分塊處理的一個簡單示例:
影象分塊程式碼
影像分塊程式碼,只有輸入輸出影象路徑,對原始影象經過一定的處理,將結果寫入輸出影象。此處原始影象和結果影象的大小完全一致。具體流程參考下面的程式碼以及裡面的註釋部分。
#include "gdal_priv.h" bool ImageProcess(const char* pszSrcFile, const char* pszDstFile, const char* pszFormat) { //註冊GDAL驅動 GDALAllRegister(); //獲取輸出影象驅動 GDALDriver *poDriver = GetGDALDriverManager()->GetDriverByName(pszFormat); if (poDriver == NULL) //輸出檔案格式錯誤 return false; //開啟輸入影象 GDALDataset *poSrcDS = (GDALDataset*)GDALOpen(pszSrcFile, GA_ReadOnly); if (poSrcDS == NULL) //輸入檔案開啟失敗 return false; //獲取輸入影象的寬高波段書 int nXSize = poSrcDS->GetRasterXSize(); int nYSize = poSrcDS->GetRasterYSize(); int nBands = poSrcDS->GetRasterCount(); //獲取輸入影象仿射變換引數 double adfGeotransform[6] = { 0 }; poSrcDS->GetGeoTransform(adfGeotransform); //獲取輸入影象空間參考 const char* pszProj = poSrcDS->GetProjectionRef(); GDALRasterBand *poBand = poSrcDS->GetRasterBand(1); if (poBand == NULL) //獲取輸入檔案中的波段失敗 { GDALClose((GDALDatasetH)poSrcDS); return false; } //建立輸出影象,輸出影象是1個波段 GDALDataset *poDstDS = poDriver->Create(pszDstFile, nXSize, nYSize, 1, GDT_Byte, NULL); if (poDstDS == NULL) //建立輸出檔案失敗 { GDALClose((GDALDatasetH)poSrcDS); return false; } //設定輸出影象仿射變換引數,與原圖一致 poDstDS->SetGeoTransform(adfGeotransform); //設定輸出影象空間參考,與原圖一致 poDstDS->SetProjection(pszProj); int nBlockSize = 256; //分塊大小 //分配輸入分塊快取 unsigned char *pSrcData = new unsigned char[nBlockSize*nBlockSize*nBands]; //分配輸出分塊快取 unsigned char *pDstData = new unsigned char[nBlockSize*nBlockSize]; //定義讀取輸入影象波段順序 int *pBandMaps = new int[nBands]; for (int b = 0; b < nBands; b++) pBandMaps[b] = b + 1; //迴圈分塊並進行處理 for (int i = 0; i < nYSize; i += nBlockSize) { for (int j = 0; j < nXSize; j += nBlockSize) { //定義兩個變數來儲存分塊大小 int nXBK = nBlockSize; int nYBK = nBlockSize; //如果最下面和最右邊的塊不夠256,剩下多少讀取多少 if (i + nBlockSize > nYSize) //最下面的剩餘塊 nYBK = nYSize - i; if (j + nBlockSize > nXSize) //最右側的剩餘塊 nXBK = nXSize - j; //讀取原始影象塊 poSrcDS->RasterIO(GF_Read, j, i, nXBK, nYBK, pSrcData, nXBK, nYBK, GDT_Byte, nBands, pBandMaps, 0, 0, 0, NULL); //再這裡填寫你自己的處理演算法 //pSrcData 就是讀取到的分塊資料,儲存順序為,先行後列,最後波段 //pDstData 就是處理後的二值圖資料,儲存順序為先行後列 memcpy(pDstData, pSrcData, sizeof(unsigned char)*nXBK*nYBK); //上面這句是一個測試,將原始影象的第一個波段資料複製到輸出的影象裡面 //寫到結果影象 poDstDS->RasterIO(GF_Write, j, i, nXBK, nYBK, pDstData, nXBK, nYBK, GDT_Byte, 1, pBandMaps, 0, 0, 0, NULL); } } //釋放申請的記憶體 delete[]pSrcData; delete[]pDstData; delete[]pBandMaps; //關閉原始影象和結果影象 GDALClose((GDALDatasetH)poSrcDS); GDALClose((GDALDatasetH)poDstDS); return true; }