cuda标准差拉伸

2024-09-02 07:38
文章标签 cuda 标准差 拉伸

本文主要是介绍cuda标准差拉伸,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

标准差拉伸(tif影像波段值类型由16bit转为8bit)cuda实现版本

用gdal2.4.4,cuda10.1 ,thrust库(计算波段均值、方差值)

  1. 使用 gdal2.4.4 读取 GTiff 格式影像,读取数据至数组
  2. 使用 thrust库计算 最大值、最小值、波段均值、方差等
  3. cuda10.1 核函数执行条件判断赋值

头文件引用

  • thrust计算最大值、最小值引用
    #include “thrust/extrema.h”

  • 设备指针
    #include “thrust/device_vector.h”

  • thrust 可以在 cpu 和 gpu 端执行
    #include “thrust/execution_policy.h”

  • 通过调用函数的第一个参数指定 thrust::reduce(thrust::host, 或 thrust:device
    在累加求和时注意总和值类型,数组类型为 unsigned short ,求和后会远远超过 该类型最大值
    auto band_sum = thrust::reduce(ptr, ptr + size, (ull)0); 指定计算类型为 unsigned long long

代码如下:

#include "cuda_runtime.h"
#include "device_launch_parameters.h"#include "thrust/host_vector.h"
#include "thrust/device_vector.h"
#include "thrust/extrema.h"
#include "thrust/reduce.h"
#include "thrust/functional.h"
#include "thrust/execution_policy.h"#include "gdal_util.h"
#include "cpl_conv.h"template<typename T1, typename T2>
struct type2_type
{__host__ __device__ T2 operator()(const T1& x) const{return static_cast<T2>(x);}
};struct variance : std::unary_function<us, double>
{variance(double m) : mean(m) { }const double mean;__host__ __device__ double operator()(us data) const{return std::pow(data - mean, 2.0);}
};// atomicCAS 暂不支持 uc__global__ void pixels_std(us* data, uc* res, const ull size, us band_max, us band_min, us uc_max, us uc_min, float k, float b)
{ui tid = threadIdx.x + blockDim.x * blockIdx.x;if (tid >= size) return;const us d = data[tid];us v;if (d == band_min)v = band_min;else if (d <= uc_min)v = band_min;else if (d >= uc_max)v = band_max;else if (k * d + b < band_min)v = band_min;else if (k * d + b > band_max)v = band_max;else if (k * d + b > band_min && k * d + b < band_max)v = k * d + b;elsev = d;res[tid] = static_cast<uc>(v);
}int main(int argc, char* argv[])
{// 16bit 转 8bitGDALAllRegister();char psz_filename[1024] = "D:\\统筹影像\\cuda\\PAN31.TIF";char psz_filename_new[1024] = "D:\\统筹影像\\cuda\\PANNew.TIF";GDALDriver* tifDriver = GetGDALDriverManager()->GetDriverByName("GTiff");CPLSetConfigOption("GDAL_FILENAME_IS_UTF8", "NO");const GDALDatasetH dataset_16bit = GDALOpen(psz_filename, GA_Update);// if (dataset == NULL)raster_info ri;get_raster_info(dataset_16bit, &ri);GDALDataset* dataset_8bit = tifDriver->Create(psz_filename_new, ri.width, ri.height, GDALGetRasterCount(dataset_16bit), GDT_Byte,NULL);dataset_8bit->SetGeoTransform(ri.geo_transform);dataset_8bit->SetProjection(ri.projection);printf("Size is %dx%dx%d\n",ri.width,ri.height,GDALGetRasterCount(dataset_8bit));printf("Pixel Size = (%.6f,%.6f)\n",ri.geo_transform[1], ri.geo_transform[5]);cudaError_t status;GDALRasterBandH h_band_16;GDALRasterBandH h_band_8;const int x_size = ri.width;const int y_size = ri.height;const ull size = x_size * y_size;const ull malloc_size = sizeof(us) * x_size * y_size;// 原影像us* h_data;uc* h_res;h_data = (us*)CPLMalloc(malloc_size);h_res = (uc*)CPLMalloc(size);// 新影像us* d_data;uc* d_res;status = cudaMalloc((void**)&d_data, malloc_size);status = cudaMalloc((void**)&d_res, size);for (int i = 0; i < 3; ++i){h_band_16 = GDALGetRasterBand(dataset_16bit, i + 1);h_band_8 = GDALGetRasterBand(dataset_8bit, i + 1);GDALRasterIO(h_band_16, GF_Read, 0, 0, x_size, y_size,h_data, x_size, y_size, GDT_UInt16, 0, 0);// 拷贝数组大小有误status = cudaMemcpy(d_data, h_data, malloc_size, cudaMemcpyHostToDevice);thrust::device_ptr<us> ptr(d_data);// 数组越界时抛出 msg:extrema failed to synchronize// 最大值最小值仅为测试函数const auto max_iter = thrust::max_element(ptr, ptr + size);const auto min_iter = thrust::min_element(ptr, ptr + size);us band_max = *max_iter;us band_min = *min_iter;band_max = 255;band_min = 0;// cpu 执行// auto band_sum_cpu = thrust::reduce(thrust::host, h_data, h_data + size, (ull)0);// gpu 执行auto band_sum = thrust::reduce(ptr, ptr + size, (ull)0);double band_mean = band_sum / (double)size;// 方差 (val-mean)*(val-mean)auto band_std2 = thrust::transform_reduce(ptr, ptr + size, variance(band_mean), (double)0, thrust::plus<double>());double band_std = std::sqrt(band_std2/(double)(size-1));float kn = 2.5;float uc_max = band_mean + kn * band_std;float uc_min = band_mean - kn * band_std;float k = (band_max - band_min) / (uc_max - uc_min);float b = (uc_max * band_min - uc_min * band_max) / (uc_max - uc_min);if (uc_min <= 0)uc_min = 0;// 标准差const ui block_size = 128;const ui grid_size = (size - 1) / block_size + 1;pixels_std << <grid_size, block_size >> > (d_data, d_res, size, band_max, band_min, uc_max, uc_min, k, b);cudaDeviceSynchronize();cudaMemcpy(h_res, d_res, size, cudaMemcpyDeviceToHost);//GDALRasterIO(h_band_8, GF_Write, 0, 0, x_size, y_size,h_res, x_size, y_size, GDT_Byte,0, 0);}cudaFree(d_data);cudaFree(d_res);CPLFree(h_data);CPLFree(h_res);GDALClose(dataset_16bit);GDALClose(dataset_8bit);return 0;
}

python版本 使用 gdal+numpy实现,GitHub链接:

python实现版本

这篇关于cuda标准差拉伸的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/1129389

相关文章

PyInstaller问题解决 onnxruntime-gpu 使用GPU和CUDA加速模型推理

前言 在模型推理时,需要使用GPU加速,相关的CUDA和CUDNN安装好后,通过onnxruntime-gpu实现。 直接运行python程序是正常使用GPU的,如果使用PyInstaller将.py文件打包为.exe,发现只能使用CPU推理了。 本文分析这个问题和提供解决方案,供大家参考。 问题分析——找不到ONNX Runtime GPU 动态库 首先直接运行python程序

CUDA:用并行计算的方法对图像进行直方图均衡处理

(一)目的 将所学算法运用于图像处理中。 (二)内容 用并行计算的方法对图像进行直方图均衡处理。 要求: 利用直方图均衡算法处理lena_salt图像 版本1:CPU实现 版本2:GPU实现  实验步骤一 软件设计分析: 数据类型: 根据实验要求,本实验的数据类型为一个256*256*8的整型矩阵,其中元素的值为256*256个0-255的灰度值。 存储方式: 图像在内存中

ffmpeg安装测试(支持cuda支持SRT)

文章目录 背景安装ffmpeg直接下载可执行文件选择版本选择对应系统版本下载测试Linux下安装 查看支持协议以及编码格式 常见错误缺少 libmvec.so.1LD_LIBRARY_PATH 错误 GPU加速测试SRT服务器搭建下载srs5.0源码解压安装配置启动 SRT推流测试SRT播放测试 背景 在音视频开发测试中,FFmpeg是一个不可或缺的工具,它以其强大的音视频处理

【FFMPEG】Install FFmpeg CUDA gltransition in Ubuntu

因为比较复杂,记录一下自己安装过程,方便后续查找,所有都是在docker环境安装cuda11.7的 **ffmpeg 4.2.2 nv-codec-headers-9.1.23.3 ** 手动下载安装吧 https://github.com/aperim/docker-nvidia-cuda-ffmpeg/blob/v0.1.10/ffmpeg/Dockerfile最好手动一个一个安装,错误跳

windows 机器学习 tensorflow-gpu +keras gpu环境的 相关驱动安装-CUDA,cuDNN。

本人真实实现的情况是: windows 10 tensorboard             1.8.0 tensorflow-gpu          1.8.0 pip install -i https://pypi.mirrors.ustc.edu.cn/simple/ tensorflow-gpu==1.8.0 Keras                   2.2.4 pip

Zxing扫描二维码精简(竖屏、拉伸处理、扫描框大小和扫描线移动、开灯)

自己在简版zxing的基础上美化了下,给大家分享下,直接扫描功能没问题。 就是从相册导入图片,解码一直不成功,导入图片解码 我引入了一个解码类  RGBLuminanceSource(百度网上二维码图片解码都是这个,我还把这个类编译了,导到core.jar包里面了), 好像是hity类型有问题,反正一直不成功。 有大神解决了,回复告诉我!谢谢! 分享 暂时没做效

CUDA与TensorRT学习三:TensorRT基础入门

文章目录 一、TensorRT概述二、TensorRT应用场景三、TensorRT模块四、导出并分析ONNX五、剖析ONNX架构并理解Protobuf六、ONNX注册算子的方法七、快速分析开源代码并导出ONNX八、使用trtexec九、trtexec log分析 一、TensorRT概述 二、TensorRT应用场景 三、TensorRT模块 四、导出并分析ONNX 五、

matlab实现kaiser窗+时域采样序列(不管原信号拉伸成什么样子)是一样的,变到频谱后再采样就是一样的频域序列。

下图窗2的频谱在周期化的时候应该是2(w-k*pi/T)我直接对2w减得写错了 可见这两个kaiser窗频谱不一样,采样间隔为2T的窗,频谱压缩2倍,且以原采样频率的一半周期化。 但是这两个不同的kaiser窗在频域采样点的值使完全一致的。这和matlab模拟dft的过程吻合 也说明不管原信号拉伸成什么样子,只要时域采样序列是一样的,变到频谱后再采样就是一样的频域序列。 (与原信号的

【并行计算】CUDA基础

cuda程序的后缀:.cu 编译:nvcc hello_world.cu 执行:./hello_world.cu 使用语言还是C++。 1. 核函数 __global__ void add(int *a, int *b, int *c) {*c = *a + *b;} 核函数只能访问GPU的内存。也就是显存。CPU的存储它是碰不到的。 并且核函数不能使用变长参数、静态变量、函数指