windows C++ 并行编程-C++ AMP 图形(二)

2024-09-01 11:52

本文主要是介绍windows C++ 并行编程-C++ AMP 图形(二),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

文中的"显存"还没有找到合适的中文翻译,它的英文名称是texture, 在应用开发者来看,texture是一个名词,在物理上指的是 GPU显存中一段连续的空间。

读取显存对象

可以使用 texture::operator[]、texture::operator() 运算符或 texture::get 方法从 texture 对象中读取。 两个运算符将返回一个值,而不是引用。 因此,你不能使用 texture 写入 texture::operator\[\] 对象。

void readTexture() {std::vector<int_2> src;for (int i = 0; i <16 *32; i++) {int_2 i2(i, i);src.push_back(i2);}std::vector<int_2> dst(16* 32);array_view<int_2, 2> arr(16, 32, dst);arr.discard_data();const texture<int_2, 2> tex9(16, 32, src.begin(), src.end());parallel_for_each(tex9.extent, [=, &tex9] (index<2> idx) restrict(amp) { // Use the subscript operator.arr[idx].x += tex9[idx].x; // Use the function () operator.arr[idx].x += tex9(idx).x; // Use the get method.arr[idx].y += tex9.get(idx).y; // Use the function () operator.arr[idx].y += tex9(idx[0], idx[1]).y;});arr.synchronize();
}

 下面的代码示例演示如何在短矢量中存储显存通道,然后访问作为短矢量属性的各个标量元素。

void UseBitsPerScalarElement() { // Create the image data. // Each unsigned int (32-bit) represents four 8-bit scalar elements(r,g,b,a values).const int image_height = 16;const int image_width = 16;std::vector<unsigned int> image(image_height* image_width);extent<2> image_extent(image_height, image_width);// By using uint_4 and 8 bits per channel, each 8-bit channel in the data source is // stored in one 32-bit component of a uint_4.texture<uint_4, 2> image_texture(image_extent, image.data(), image_extent.size()* 4U,  8U);// Use can access the RGBA values of the source data by using swizzling expressions of the uint_4.parallel_for_each(image_extent,[&image_texture](index<2> idx) restrict(amp){ // 4 bytes are automatically extracted when reading.uint_4 color = image_texture[idx];unsigned int r = color.r;unsigned int g = color.g;unsigned int b = color.b;unsigned int a = color.a;});
}

 下表列出了每种短矢量类型的每通道有效位数。

 写入显存对象

使用 texture::set 方法可写入 texture 对象。 显存对象可以是只读或读/写属性。 显存对象若要可读写,必须满足以下条件:

T 只有一个标量组件。 (不允许使用短矢量。)

T 不是 double、norm 或 unorm。

texture::bits_per_scalar_element 属性为 32。

如果不符合这三个条件,则 texture 对象为只读对象。 编译期间将检查前两个条件。 如果有代码尝试写入 readonly 显存对象,将产生编译错误。 texture::bits_per_scalar_element 条件在运行时进行检查,如果尝试写入只读的 texture 对象,则运行时将产生 unsupported_feature 异常。

下面的代码示例向一个显存对象写入了多个值。

void writeTexture() {texture<int, 1> tex1(16);parallel_for_each(tex1.extent, [&tex1] (index<1> idx) restrict(amp) {tex1.set(idx, 0);});
}
 复制显存对象

如下面的代码示例所示,可以使用 copy 函数或 copy_async 函数在显存对象之间进行复制。

void copyHostArrayToTexture() { // Copy from source array to texture object by using the copy function.float floatSource[1024* 2];for (int i = 0; i <1024* 2; i++) {floatSource[i] = (float)i;}texture<float_2, 1> floatTexture(1024);copy(floatSource, (unsigned int)sizeof(floatSource), floatTexture);// Copy from source array to texture object by using the copy function.char charSource[16* 16];for (int i = 0; i <16* 16; i++) {charSource[i] = (char)i;}texture<int, 2> charTexture(16, 16, 8U);copy(charSource, (unsigned int)sizeof(charSource), charTexture);// Copy from texture object to source array by using the copy function.copy(charTexture, charSource, (unsigned int)sizeof(charSource));
}

你还可以使用 texture::copy_to 方法从一个纹理复制到另一个纹理。 这两个纹理可以位于不同的 accelerator_view 上。 当复制到 writeonly_texture_view 对象时,数据将复制到基础 texture 对象。 源和目标 texture 对象上的每标量元素位数和范围必须相同。 如果不符合这些需求,运行时将引发异常。

显存视图类

C++ AMP 介绍了 Visual Studio 2013 中的 texture_view 类。 显存视图支持与 texture 类相同的纹素类型和秩,但是与显存不同,它们允许访问其他硬件功能,如显存采样和 mipmap。 显存视图支持对基础显存数据进行只读、只写和读/写访问。

  • 只读访问由 texture_view<const T, N> 模板专用化提供,支持具有 1 个、2 个或 4 个组件的元素、显存采样以及动态访问在实例化视图时确定的一系列 mipmap 级别;
  • 写入访问由非专用模板类 texture_view<T, N> 提供,支持具有 2 个或 4 个组件的元素,并且可以访问在实例化视图时确定的一个 mipmap 级别。 它不支持采样;
  • 读写访问由非专用模板类 texture_view<T, N> 提供,与显存一样,支持仅具有 1 个组件的元素;视图可以访问在实例化视图时确定的一个 mipmap 级别。 它不支持采样;

显存视图类似于数组视图,但是不提供 array_view 类通过 array 类提供的自动数据管理和移动功能。 texture_view 只能在基础显存数据所在的快捷键视图中进行访问。

这篇关于windows C++ 并行编程-C++ AMP 图形(二)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



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

相关文章

C++使用printf语句实现进制转换的示例代码

《C++使用printf语句实现进制转换的示例代码》在C语言中,printf函数可以直接实现部分进制转换功能,通过格式说明符(formatspecifier)快速输出不同进制的数值,下面给大家分享C+... 目录一、printf 原生支持的进制转换1. 十进制、八进制、十六进制转换2. 显示进制前缀3. 指

C++中初始化二维数组的几种常见方法

《C++中初始化二维数组的几种常见方法》本文详细介绍了在C++中初始化二维数组的不同方式,包括静态初始化、循环、全部为零、部分初始化、std::array和std::vector,以及std::vec... 目录1. 静态初始化2. 使用循环初始化3. 全部初始化为零4. 部分初始化5. 使用 std::a

shell编程之函数与数组的使用详解

《shell编程之函数与数组的使用详解》:本文主要介绍shell编程之函数与数组的使用,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教... 目录shell函数函数的用法俩个数求和系统资源监控并报警函数函数变量的作用范围函数的参数递归函数shell数组获取数组的长度读取某下的

C++ vector的常见用法超详细讲解

《C++vector的常见用法超详细讲解》:本文主要介绍C++vector的常见用法,包括C++中vector容器的定义、初始化方法、访问元素、常用函数及其时间复杂度,通过代码介绍的非常详细,... 目录1、vector的定义2、vector常用初始化方法1、使编程用花括号直接赋值2、使用圆括号赋值3、ve

Redis在windows环境下如何启动

《Redis在windows环境下如何启动》:本文主要介绍Redis在windows环境下如何启动的实现方式,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教... 目录Redis在Windows环境下启动1.在redis的安装目录下2.输入·redis-server.exe

如何高效移除C++关联容器中的元素

《如何高效移除C++关联容器中的元素》关联容器和顺序容器有着很大不同,关联容器中的元素是按照关键字来保存和访问的,而顺序容器中的元素是按它们在容器中的位置来顺序保存和访问的,本文介绍了如何高效移除C+... 目录一、简介二、移除给定位置的元素三、移除与特定键值等价的元素四、移除满足特android定条件的元

Python获取C++中返回的char*字段的两种思路

《Python获取C++中返回的char*字段的两种思路》有时候需要获取C++函数中返回来的不定长的char*字符串,本文小编为大家找到了两种解决问题的思路,感兴趣的小伙伴可以跟随小编一起学习一下... 有时候需要获取C++函数中返回来的不定长的char*字符串,目前我找到两种解决问题的思路,具体实现如下:

C++ Sort函数使用场景分析

《C++Sort函数使用场景分析》sort函数是algorithm库下的一个函数,sort函数是不稳定的,即大小相同的元素在排序后相对顺序可能发生改变,如果某些场景需要保持相同元素间的相对顺序,可使... 目录C++ Sort函数详解一、sort函数调用的两种方式二、sort函数使用场景三、sort函数排序

Java调用C++动态库超详细步骤讲解(附源码)

《Java调用C++动态库超详细步骤讲解(附源码)》C语言因其高效和接近硬件的特性,时常会被用在性能要求较高或者需要直接操作硬件的场合,:本文主要介绍Java调用C++动态库的相关资料,文中通过代... 目录一、直接调用C++库第一步:动态库生成(vs2017+qt5.12.10)第二步:Java调用C++

C/C++错误信息处理的常见方法及函数

《C/C++错误信息处理的常见方法及函数》C/C++是两种广泛使用的编程语言,特别是在系统编程、嵌入式开发以及高性能计算领域,:本文主要介绍C/C++错误信息处理的常见方法及函数,文中通过代码介绍... 目录前言1. errno 和 perror()示例:2. strerror()示例:3. perror(