GDAL C++ API 学习之路 (5) Dataset篇 代码示例 翻译 自学

BuildOverviews

CPLErr BuildOverviews(const char*, int, const int*, int, const int*, GDALProgressFunc, void*, CSLConstList papszOptions)      此方法与 C 函数 GDALBuildOverviewsEx() 相同

构建栅格概览

参数:

  • pszResampling – 控制所应用的下采样方法

  • nResampling – 要构建的概览数,或 0 以清理概览。

  • panOverviewList – 要构建的概览抽取因子列表,如果 nOverviews == 0,则为 NULL。

  • nListBands – 要在 panBandList 中构建概览的波段数。如果此值为 0,则为所有波段构建。

  • panBandList ― 乐队编号列表。

  • pfnProgress – 用于调用以报告进度或 NULL 的函数。

  • pProgressData – 要传递给进度函数的应用程序数据。

  • papszOptions – (GDAL >= 3.6) NULL 终止的选项列表作为键=值对,或 NULL

返回: CE_None成功或CE_Failure如果操作不起作用

pszResampling

  1. 最邻近采样(Nearest Neighbour):即在输入栅格数据上选取与输出栅格数据最近的像素值作为输出像素值。最邻近采样是速度最快的一种采样方法,但是在对连续变化的数据进行预览时,其输出结果可能会有明显的锯齿状。

  2. 双线性插值(Bilinear Interpolation):双线性插值方法是一种基于四个最近邻像素值加权平均的方法,用于计算输出像素值。这种方法相对于最邻近采样方法来说会更加平滑,但是速度略慢。

  3. 三次卷积(Cubic Convolution):三次卷积方法是一种基于16个最近邻像素值的插值方法,与双线性插值相比,它能够更加准确地插值。但是其计算量比较大,速度也相应地慢一些。

  4. 平均值采样(Average):平均值采样方法是一种简单的像素均值计算方法,它会计算在输入栅格数据中所有像素值的平均值,并将该平均值作为输出像素值。这种方法的主要优点是速度非常快,但是可能会导致输出图像的细节丢失。

还有"AVERAGE_MAGPHASE"、“立方体”、“立方样”、“高斯”、“兰索斯”、“模式”或“无” 

GDALDataset* poSrcDS = (GDALDataset*)GDALOpen("input.tif", GA_ReadOnly);
int nOverviews = 4;
int panOverviewList[] = { 2, 4, 8, 16 };

// 构建预览图
CPLErr err = poSrcDS->BuildOverviews("NEAREST", nOverviews, panOverviewList, 0, NULL, GDALDummyProgress, NULL, NULL);

panOverview 是一个泛概述列表(因子)

上例的代码中,2,4,8,16分别代表了第一、二、三、四不同的级别,每个级别的像素数是前一个级别的四倍。因此,如果原始图像的大小为1024x1024像素,第一级别的大小将是512x512像素,第二级别的大小将是256x256像素,以此类推,直到第八级别的大小为2x2像素

GetMetadata

virtual char **GetMetadata(const char *pszDomain = "") override  表示该函数重写了基类中的同名函数        此方法与 C 函数 GDALGetMetadata() 执行相同的操作

参数:

pszDomain – 感兴趣的域。使用“”或 NULL 作为默认域。

返回: NULL 或字符串列表

char **metadata = dataset->GetMetadata();
if (metadata != nullptr) {
    for (int i = 0; metadata[i] != nullptr; i++) {
        // 遍历元数据
        printf("%s\n", metadata[i]);
    }
}

    //使用 CPL StringList 函数(如 CSLFetchNameValue() 来操作它
 const char* pszDescription = CSLFetchNameValue(metadata, "Description");

// 输出名为"Description"的键的值
printf("Description: %s\n", pszDescription);

AREA_OR_POINT=Area
BandDefinitionKeyword=*
DataType=*

Description: (null)

SetMetadata

virtual CPLErr SetMetadata(char **papszMetadata, const char *pszDomain) override          C 函数 GDALSetMetadata() 与此方法执行相同的操作

 设置元数据

参数:

  • papszMetadata – 要应用的名称=值字符串列表格式的元数据。

  • pszDomain – 感兴趣的域。使用“”或 NULL 作为默认域。

返回: CE_None成功时,CE_Failure失败时,CE_Warning元数据是否已被接受,但可能不会由会话之间的基础对象永久维护。

char *papszMetadata[] = {"DESCRIPTION=This is a test image", "AUTHOR=John Doe", NULL};
poDS->SetMetadata(papszMetadata, "IMAGE_STRUCTURE");

SetMetadataItem

virtual CPLErr SetMetadataItem(const char *pszName, const char *pszValue, const char *pszDomain)override       C 函数 GDALSetMetadataItem() 与此方法执行相同的操作

设置单个元数据项

参数:

  • pszName – 要提取的元数据项的键。

  • pszValue – 要分配给键的值。

  • pszDomain – 要在其中设置的域,使用 NULL 作为默认域。

返回: 成功时CE_None,失败时错误代码。

poDS->SetMetadataItem("DESCRIPTION", "This is a test image");
poDS->SetMetadataItem("AUTHOR", "John Doe", "IMAGE_STRUCTURE");
  • GLOBAL: 全局元数据,适用于整个数据集。
  • RPC: 存储了一些与有理多项式相关的元数据,通常用于遥感图像数据。
  • GEOLOCATION: 存储了一些与地理位置相关的元数据,通常用于将栅格数据与地理位置信息相对应。
  • COLOR_TABLE: 存储了与颜色表相关的元数据,通常用于存储栅格数据的颜色表信息。
  • IMAGE_STRUCTURE: 存储了一些与栅格数据结构相关的元数据,如数据块大小、压缩参数等。

GetMetadataDomainList

virtual char **GetMetadataDomainList() override          此方法与 C 函数 GDALGetMetadataDomainList() 执行相同的操作

返回: NULL 或字符串列表。必须使用 CSLDestroy() 释放

GDALDataset* poDataset = static_cast<GDALDataset*>(GDALOpen("path/to/raster/file", GA_ReadOnly));
char** papszMetadataDomains = poDataset->GetMetadataDomainList();
    cout << "Metadata domains:" << endl;
    for (char** ppMetadataDomain = papszMetadataDomains; *ppMetadataDomain != nullptr; ppMetadataDomain++) {
        cout << "- " << *ppMetadataDomain << endl;
    }

    // 释放资源
    CSLDestroy(papszMetadataDomains);
    GDALClose(poDataset);

ClearStatistics  

virtual void ClearStatistics()        与 C 函数 GDALDatasetClearStatistics() 相同

清晰的统计数据      目前仅在 PAM 支持的数据集中实现

GetLayerCount

virtual int GetLayerCount()                此方法与 C 函数 GDALDatasetGetLayerCount() 和已弃用的 OGR_DS_GetLayerCount() 相同

获取此数据集中的图层数

返回:  层数

GetLayer

virtual OGRLayer *GetLayer(int iLayer)  

按索引获取图层

参数:

iLayer – 介于 0 和 GetLayerCount()-1 之间的层数。

返回:  图层,如果 iLayer 超出范围或发生错误,则为 NULL

OGRLayer *poLayer = poDS->GetLayer(0);

返回的层仍归 GDALDataset 所有,应用程序不应删除该层

获取到的 GDALRasterLayer 对象属于 GDALDataset 对象的一个指针,由 GDALDataset 对象管理和销毁。如果应用程序删除该层,可能会导致 GDALDataset 对象指向已被删除的内存,从而导致错误

OGRLayer会在矢量API部分的OGRLayer C++ API 详细学习:

http://t.csdn.cn/KpRHU

IsLayerPrivate

virtual bool IsLayerPrivate(int iLayer) const        此方法与 C 函数 GDALDatasetIsLayerPrivate() 相同

如果指定索引处的图层被视为私有表或系统表,或者仅被视为内部详细信息

参数:

iLayer – 介于 0 和 GetLayerCount()-1 之间的层数。

返回: 如果图层是专用表或系统表,则为 true

poLayer = poDS->GetLayer(0);

// 检查层是否私有
if (poLayer->IsLayerPrivate()) {
    printf("Layer is private.\n");
} else {
    printf("Layer is not private.\n");
}

GetLayers

Layers GetLayers()                 GetLayer() 的C++迭代器友好版本

在数据集中的图层上返回可迭代对象的函数

int nLayers = poDS->GetLayerCount();
printf("图层数量:%d\n", nLayers);

// 获取图层列表并进行迭代
GDALDataset::LayerIterator iter = poDS->GetLayers();
for (int i = 0; i < nLayers; i++, iter++) {
    OGRLayer* poLayer = iter;
    printf("图层 %d 名称:%s\n", i, poLayer->GetName());
}

GetLayerByName

virtual OGRLayer *GetLayerByNameconst char*)        此方法与 C 函数 GDALDatasetGetLayerByName() 和已弃用的 OGR_DS_GetLayerByName() 相同

按名称获取图层

参数:

pszName – 要获取的图层的图层名称。

返回: 图层,如果未找到图层或发生错误,则为 NULL

GDALDataset* poDS = (GDALDataset*) GDALOpen("example.tif", GA_ReadOnly);
OGRLayer *poLayer = poDS->GetLayerByName("example_layer");
if (poLayer == NULL) {
    printf("Layer not found\n");
} else {
    printf("Layer found!\n");
}

DeleteLayer

virtual OGRErr DeleteLayer(int iLayer)        此方法与 C 函数 GDALDatasetDeleteLayer() 和已弃用的 OGR_DS_DeleteLayer() 相同

从数据源中删除指示的图层

参数:

iLayer – 要删除的图层的索引。

返回:  成功时OGRERR_NONE,如果此数据源不支持删除图层,则OGRERR_UNSUPPORTED_OPERATION

GDALDataset* poDataset;
int nLayerIndex = 0; //要删除的图层索引
OGRLayer* poLayer = poDataset->GetLayer(nLayerIndex);

if (poLayer != NULL) {
    poDataset->DeleteLayer(nLayerIndex);
    delete poLayer;
}

ResetReading

virtual void ResetReading()                此方法与 C 函数 GDALDatasetResetReading() 相同

重置特征读取以从第一个特征开始    该函数可以将指针指向图层中第一个特征的位置

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
当然,以下是一个基于GDAL的C++示例代码,实现了窗口为5的极化均值滤波: ```c++ #include <iostream> #include "gdal_priv.h" #include "cpl_conv.h" int main() { // 打开二进制文件,读取数据并转换为GDAL数据集 const char *filename = "your_bin_file.bin"; int rows = 1000; // 影像数据的行数 int cols = 1000; // 影像数据的列数 GDALAllRegister(); GDALDataset *ds = (GDALDataset*)GDALOpen(filename, GA_ReadOnly); double *data = new double[rows * cols]; CPLErr err = ds->RasterIO(GF_Read, 0, 0, cols, rows, data, cols, rows, GDT_Float64, 0, 0); if (err != CE_None) { std::cout << "Error reading file: " << GDALGetLastErrorMsg() << std::endl; return 1; } // 定义窗口大小和边缘宽度 int win_size = 5; int edge_width = (win_size - 1) / 2; // 构建输出数组 double *output = new double[rows * cols]; // 极化均值滤波函数 double polar_mean_filter(double *data, int x, int y, int win_size) { double win[25]; int k = 0; for (int i = x - edge_width; i <= x + edge_width; i++) { for (int j = y - edge_width; j <= y + edge_width; j++) { win[k++] = data[i * cols + j]; } } std::sort(win, win + win_size * win_size); double filtered[21]; for (int i = 0; i < 21; i++) { filtered[i] = win[i + 2]; // 去除最大和最小值 } double sum = 0.0; for (int i = 0; i < 21; i++) { sum += filtered[i]; } double mean = sum / 21.0; return mean; } // 循环遍历每个像素点,并进行滤波 for (int i = edge_width; i < rows - edge_width; i++) { for (int j = edge_width; j < cols - edge_width; j++) { output[i * cols + j] = polar_mean_filter(data, i, j, win_size); } } // 将输出数组写入二进制文件 GDALDriver *driver = GetGDALDriverManager()->GetDriverByName("ENVI"); GDALDataset *out_ds = driver->Create("output.bin", cols, rows, 1, GDT_Float64, NULL); out_ds->RasterIO(GF_Write, 0, 0, cols, rows, output, cols, rows, GDT_Float64, 0, 0); out_ds->FlushCache(); GDALClose(out_ds); delete[] data; delete[] output; GDALClose(ds); return 0; } ``` 以上代码中,首先通过`GDALOpen()`函数打开二进制文件,并使用`GDALDataset::RasterIO()`函数读取数据到内存中。然后定义窗口大小和边缘宽度,以及输出数组。接着定义了一个极化均值滤波函数,该函数接受一个一维数组、中心像素点的位置以及窗口大小作为输入,返回滤波后的像素值。最后,循环遍历每个像素点,并使用`polar_mean_filter()`函数进行滤波,将结果存储到输出数组中,并使用GDAL的函数将输出数组写入二进制文件中。 需要注意的是,以上代码仅供参考,具体实现方法还需要根据您的数据格式和算法要求进行调整。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

场主不吃鍋巴

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值