GDAL C++ RasterIO的块
问题描述:
我是gdal和C++的新手,我试图创建一个按块(使用RasterIO而不是ReadBlock)读取栅格的函数,并将结果写入新的栅格文件GDAL C++ RasterIO的块
我得到一个错误:
Unhandled exception at 0x00007FFDFB517BC4 (gdal201.dll) in Test.exe: 0xC0000005: Access violation writing location 0x00000230E2593000 at line rasterBand->RasterIO(GDALRWFlag::GF_Read, j * readCols, i * readRows, readCols, readRows, rasterBlock, readCols, readRows, GDALDataType::GDT_CFloat32, 0, 0)
我有一个非常类似的功能工作正常,但按行
任何帮助表示赞赏读取的像素值排
功能是波纹管
谢谢
#include <iostream>
#include "gdal_priv.h"
using namespace std;
void SlopeBlock()
{
int readRows = 2048;
int readCols = 2048;
int nBlockXSize;
int nBlockYSize;
int rowOff = 0;
int colOff = 0;
int nRows = 0;
int nCols = 0;
double noData = -9999;
GDALAllRegister();
GDALDataset* dem = (GDALDataset*)GDALOpen("path/EUD_CP-DEMS_4500025000-AA.tif", GA_ReadOnly);
GDALDriver *gTIF = GetGDALDriverManager()->GetDriverByName(dem->GetDriverName());
double geoTransform[6];
dem->GetGeoTransform(geoTransform);
GDALRasterBand* rasterBand = dem->GetRasterBand(1);
nCols = rasterBand->GetXSize();
nRows = rasterBand->GetYSize();
noData = rasterBand->GetNoDataValue();
//rasterBand->GetBlockSize(&nBlockXSize, &nBlockYSize);
int nXBlocks = (rasterBand->GetXSize() + readCols - 1)/readCols;
int nYBlocks = (rasterBand->GetYSize() + readRows - 1)/readRows;
cout << nYBlocks << "___" << nXBlocks << "\n";
//Slope
GDALDataset *slope = gTIF->Create("path/slopeBlock.tif", nCols, nRows, 1, GDT_Float32, NULL);
slope->SetGeoTransform(geoTransform);
for (int i = 0; i < nYBlocks; i++)
{
for (int j = 0; j < nXBlocks; j++)
{
float* rasterBlock = (float*)CPLMalloc(readCols*readRows*sizeof(float));
float* rasterBlockOut = (float*)CPLMalloc(readCols*readRows*sizeof(float));
if (rasterBand != nullptr)
rasterBand->RasterIO(GDALRWFlag::GF_Read, j * readCols, i * readRows, readCols, readRows, rasterBlock, readCols, readRows, GDALDataType::GDT_CFloat32, 0, 0);
//Not sure if is working
for (int jb = 0; jb < readCols; jb++)
{
if (rasterBlock[jb] == noData)
{
rasterBlockOut[jb] = noData;
}
else
{
rasterBlockOut[jb] = rasterBlock[jb];
}
}
slope->GetRasterBand(1)->RasterIO(GDALRWFlag::GF_Write, j * readCols, i * readRows, readCols, readRows, rasterBlockOut, readCols, readRows, GDALDataType::GDT_CFloat32, 0, 0);
CPLFree(rasterBlock);
CPLFree(rasterBlockOut);
}
}
GDALClose(dem);
GDALClose(slope);
}
答
这可能不是飞机坠毁的原因,但你问一个2048 * 2048块就算你的形象是较小。此代码只适用于尺寸为2048的倍数的图像。
你应该这样做:
nXSize = min(readCols, rasterBand->GetXSize() - j * readCols);
nYSize = min(readRows, rasterBand->GetYSize() - i * readRows);
rasterBand->RasterIO(GDALRWFlag::GF_Read, j * readCols, i * readRows,
nXSize, nYSize, rasterBlock, nXSize, nYSize, GDALDataType::GDT_CFloat32, 0, 0);
谢谢您的帮助。下面的代码正在工作,但是这样做比读取整个图像需要更多时间。 我改变了 \t float * rasterBlock =(float *)CPLMalloc(nCols * nRows * sizeof(GDT_CFloat32)); \t float * rasterBlockOut =(float *)CPLMalloc(nCols * nRows * sizeof(GDT_CFloat32)); –
使用块的目的不是加速处理(如果处理整个图像),而是要处理大量不适合内存的数据。如果你可以在RAM中一次加载整个图像,它肯定会更快。 – Gwen