#include <stdio.h> #include <stdlib.h> #include 'tiffio.h'

#define ROWS 327 #define COLS 486 #define PIXEL_SIZE 5 #define TILE_SIZE 64

int main(int argc, char* argv[]) { TIFF* tif; float* data; uint32_t width, height; uint16_t bits_per_sample, samples_per_pixel; tsize_t tile_size; float min_elevation = 1e9, max_elevation = -1e9; unsigned long long total_fill_volume = 0, total_cut_volume = 0; int i, j, tile_row, tile_col;

if (argc < 2) {
    fprintf(stderr, "Usage: %s <input file>

", argv[0]); exit(1); }

tif = TIFFOpen(argv[1], "r");
if (!tif) {
    fprintf(stderr, "Error opening TIFF file

"); exit(1); }

TIFFGetField(tif, TIFFTAG_IMAGEWIDTH, &width);
TIFFGetField(tif, TIFFTAG_IMAGELENGTH, &height);
TIFFGetField(tif, TIFFTAG_BITSPERSAMPLE, &bits_per_sample);
TIFFGetField(tif, TIFFTAG_SAMPLESPERPIXEL, &samples_per_pixel);

if (width != COLS || height != ROWS || bits_per_sample != 32 || samples_per_pixel != 1) {
    fprintf(stderr, "Invalid TIFF format

"); exit(1); }

tile_size = TIFFTileSize(tif);
data = (float*)_TIFFmalloc(tile_size);
if (!data) {
    fprintf(stderr, "Error allocating memory

"); exit(1); }

if (!TIFFIsTiled(tif)) {
    fprintf(stderr, "Can not read tiles from a non-tiled image.

"); exit(1); }

for (tile_row = 0; tile_row < height; tile_row += TILE_SIZE) {
    for (tile_col = 0; tile_col < width; tile_col += TILE_SIZE) {
        TIFFReadTile(tif, data, tile_col, tile_row, 0, 0);
        min_elevation = data[0]; // 初始化最小高程值为第一个读取的高程值
        for (i = 0; i < TILE_SIZE && tile_row + i < height; i++) {
            for (j = 0; j < TILE_SIZE && tile_col + j < width; j++) {
                float elevation = data[i * TILE_SIZE + j];
                if (elevation > max_elevation) {
                    max_elevation = elevation;
                }
                if (elevation < min_elevation) {
                    min_elevation = elevation;
                }
            }
        }
        for (i = 0; i < TILE_SIZE && tile_row + i < height; i++) {
            for (j = 0; j < TILE_SIZE && tile_col + j < width; j++) {
                float elevation = data[i * TILE_SIZE + j];
                if (elevation <= max_elevation) { // 如果高程值小于等于最大值,进行填方
                    total_fill_volume += (PIXEL_SIZE * PIXEL_SIZE * (max_elevation - elevation));
                }
                if (elevation >= min_elevation) { // 如果高程值大于等于最小值,进行挖方
                    total_cut_volume += (PIXEL_SIZE * PIXEL_SIZE * (elevation - min_elevation));
                }
            }
        }
    }
}

printf("Min elevation: %.3f meters

", min_elevation); printf("Max elevation: %.3f meters ", max_elevation); printf("Total fill volume: %.3f cubic kilometers ", total_fill_volume / 1e9); printf("Total cut volume: %.3f cubic kilometers ", total_cut_volume / 1e9);

_TIFFfree(data);
TIFFClose(tif);

return 0;

}

详细解释内容:这是一个处理地形数据的程序,它读取一个 TIFF 格式的高程数据文件,计算出最小高程值、最大高程值、填方体积和挖方体积,并输出这些结果。

程序的主要流程如下:

  1. 打开 TIFF 文件,读取文件信息,包括图像宽度、高度、每个像素的位数和每个像素的通道数。
  2. 检查 TIFF 文件的格式是否符合要求,如果不符合则退出程序。
  3. 分块读取 TIFF 文件中的高程数据,每个块的大小为 64x64,计算每个块的最小高程值和最大高程值。
  4. 对于每个像素,如果其高程值小于等于最大高程值,则计算填方体积;如果其高程值大于等于最小高程值,则计算挖方体积。
  5. 输出最小高程值、最大高程值、填方体积和挖方体积。

程序中用到的一些关键函数和变量的解释如下:

  1. TIFFOpen:打开 TIFF 文件。
  2. TIFFGetField:读取 TIFF 文件的信息,包括图像宽度、高度、每个像素的位数和每个像素的通道数。
  3. TIFFIsTiled:检查 TIFF 文件是否是分块存储的。
  4. TIFFTileSize:获取每个块的大小。
  5. TIFFReadTile:读取一个块的数据。
  6. _TIFFmalloc:分配内存。
  7. _TIFFfree:释放内存。

其中,变量 ROWS、COLS、PIXEL_SIZE 和 TILE_SIZE 分别表示图像的行数、列数、像素大小和块的大小。变量 min_elevation、max_elevation、total_fill_volume 和 total_cut_volume 分别表示最小高程值、最大高程值、填方体积和挖方体积。变量 data 是存储高程数据的缓冲区。变量 i、j、tile_row 和 tile_col 是循环计数器,用于遍历每个像素和每个块。

C语言TIFF高程数据处理:计算填挖方体积

原文地址: http://www.cveoy.top/t/topic/fVkx 著作权归作者所有。请勿转载和采集!

免费AI点我,无需注册和登录