《C++ AMP:用Visual C++加速大规模并行计算》——3.7 使用restrict(amp)标记的函数

简介:

本节书摘来自异步社区出版社《C++ AMP:用Visual C++加速大规模并行计算》一书中的第3章,第3.7节,作者: 【美】Kate Gregory , Ade Miller,更多章节内容可以访问云栖社区“异步社区”公众号查看。

3.7 使用restrict(amp)标记的函数

C++ AMP:用Visual C++加速大规模并行计算
要想成功地使用restrict(amp)编译,函数必须遵守许多规则。头一条规则我们在3.6节中提到过,与其调用的函数有关。这些规则必须在代码生成时是可见的,也必须使用restrict(amp)进行标记。如果我们没有使用链接时代码生成,基本上就意味着它们一定要和编译时的.cpp文件相同,也可以使用那个.cpp文件中包含的头文件带进来。如果在编译两个.cpp文件(一个调用函数的和一个实现函数的)时,还有链接时,使用/ltcg开关,那么调用函数和被调用函数就可以放在各自独立的文件里。

C++ AMP兼容函数或lambda表达式只能使用C++ AMP兼容类型,它们包括:

int
unsigned int
float
double
C风格的intunsigned int、floatdouble数组
concurrency::array引用或concurrency::array_view
只含有C++ AMP兼容类型的结构体
这也意味着某些数据类型是禁止使用的:

bool(可以在lambda表达式中用于本地变量)
char
short
long long
上述类型的无符号版本
引用和指针(指向兼容类型)可以在本地使用,但不能传入lambda。函数指针、指向指针的指针等不能使用;静态变量或全局变量也不能使用。

如果要使用类实例,那么类必须满足更多规则。它们不能是虚函数或虚拟继承。构造函数、析构函数以及其他非虚函数都可以使用。成员变量必须全部是兼容类型,当然也可以包含其他类的实例,只要这些类能满足相同的规则。

amp兼容函数中的实际代码不是在CPU中运行的,因此不能用来做下面的事情:

递归
指针类型转换
使用虚函数
newdelete
RTTI或动态类型转换
goto
throwtrycatch
访问全局变量或静态变量
内联汇编
如果我们违反了这些规则,那么看看编译器抛出的错误消息会有所帮助。下面的代码满足所有规则,可以无错编译:

std::vector<int> v(5);
std::iota(v.begin(), v.end(), 0);
array<int, 1> a(5, v.begin(), v.end());
parallel_for_each(a.extent, [&](index<1> idx) restrict(amp)
{
   a[idx] = a[idx] * 2;
});```
现在把lambda中没有使用restrict(amp)标记的调用函数替换掉,但还放在同一个.cpp文件里,我们会看到下面的提示(DoubleIt是被调用函数的名字):

error C3930: 'DoubleIt' : no overloaded function has restriction specifiers that are compatible
with the ambient context`
如果函数有对应的限制,但在代码生成时不可见,那么我们也会看到这条消息。

如果我们使用short等类型,会因为restrict(amp)代码并不支持它们,而会看到如下的错误消息:

error C3581: 'short': unsupported type in amp restricted code
如果尝试声明指向指针的指针或者其他未经支持的类型,都会看到同样的消息。

相关文章
|
2月前
|
程序员 C++ 容器
在 C++中,realloc 函数返回 NULL 时,需要手动释放原来的内存吗?
在 C++ 中,当 realloc 函数返回 NULL 时,表示内存重新分配失败,但原内存块仍然有效,因此需要手动释放原来的内存,以避免内存泄漏。
|
2月前
|
存储 前端开发 C++
C++ 多线程之带返回值的线程处理函数
这篇文章介绍了在C++中使用`async`函数、`packaged_task`和`promise`三种方法来创建带返回值的线程处理函数。
49 6
|
2月前
|
C++
C++ 多线程之线程管理函数
这篇文章介绍了C++中多线程编程的几个关键函数,包括获取线程ID的`get_id()`,延时函数`sleep_for()`,线程让步函数`yield()`,以及阻塞线程直到指定时间的`sleep_until()`。
25 0
C++ 多线程之线程管理函数
|
2月前
|
编译器 C语言 C++
C++入门3——类与对象2-2(类的6个默认成员函数)
C++入门3——类与对象2-2(类的6个默认成员函数)
29 3
|
2月前
|
编译器 C语言 C++
详解C/C++动态内存函数(malloc、free、calloc、realloc)
详解C/C++动态内存函数(malloc、free、calloc、realloc)
205 1
|
2月前
|
存储 编译器 C++
C++入门3——类与对象2-1(类的6个默认成员函数)
C++入门3——类与对象2-1(类的6个默认成员函数)
35 1
|
2月前
|
编译器 C语言 C++
C++入门6——模板(泛型编程、函数模板、类模板)
C++入门6——模板(泛型编程、函数模板、类模板)
47 0
C++入门6——模板(泛型编程、函数模板、类模板)
|
3月前
|
C++ 内存技术
[转]Visual C++内嵌swf文件并播放
[转]Visual C++内嵌swf文件并播放
|
3月前
|
编译器 C++
【C++核心】函数的应用和提高详解
这篇文章详细讲解了C++函数的定义、调用、值传递、常见样式、声明、分文件编写以及函数提高的内容,包括函数默认参数、占位参数、重载等高级用法。
24 3
|
4月前
|
编译器 C++ 容器
【C++】String常见函数用法
【C++】String常见函数用法