- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
大家好。我正在使用 AMP C++ 进行一些体积计算。
我有数百万个四面体,其中一个点位于 (0,0,0)。所以我可以用一种简单的方式得到四面体的体积:
sum += triangle.x1 * triangle.y2 * triangle.z3 + \
triangle.y1 * triangle.z2 * triangle.x3 + \
triangle.x2 * triangle.y3 * triangle.z1 - \
triangle.x3 * triangle.y2 * triangle.z1 - \
triangle.x2 * triangle.y1 * triangle.z3 - \
triangle.y3 * triangle.z2 * triangle.x1;
所以,我想通过使用 AMP C++ 来加快计算速度。
这是代码。
typedef struct
{
double x1;
double y1;
double z1;
double x2;
double y2;
double z2;
double x3;
double y3;
double z3;
} Triangle;
主要功能是:
accelerator my_accelerator(accelerator::default_accelerator);
accelerator_view acc_view = my_accelerator.get_default_view();
const int BLOCK_SIZE = 64;
int outputSize = int(numTriangles / BLOCK_SIZE);
int dimA = int(numTriangles / BLOCK_SIZE) * BLOCK_SIZE;
std::cout<<dimA<<std::endl;
//copy triangles from host to device
array<Triangle,1> triangle(numTriangles);
copy(vTriangle.begin(),vTriangle.end(), triangle);
//Volume
std::vector<double> volumeCPP;
for (int i=0; i < outputSize; i++)
{
volumeCPP.push_back(double(0));
}
array_view<double,1> volume(outputSize,volumeCPP);
volume.discard_data();
clock_t start,finish;
start = clock();
parallel_for_each(
volume.extent.tile<1>(),
[=, &triangle](tiled_index<1> t_idx) restrict(amp)
{
double sum = 0.0f;
tile_static Triangle tile_triangle[4];
tile_triangle[t_idx.local[0]] = triangle[t_idx.global];
if (t_idx.local[0] == 0)
{
for (int idx=0; idx < BLOCK_SIZE; idx++){
sum += tile_triangle[idx].x1 * tile_triangle[idx].y2 * tile_triangle[idx].z3 + tile_triangle[idx].y1 * tile_triangle[idx].z2 * tile_triangle[idx].x3 + tile_triangle[idx].x2 * tile_triangle[idx].y3 * tile_triangle[idx].z1 - tile_triangle[idx].x3 * tile_triangle[idx].y2 * tile_triangle[idx].z1 - tile_triangle[idx].x2 * tile_triangle[idx].y1 * tile_triangle[idx].z3 - tile_triangle[idx].y3 * tile_triangle[idx].z2 * tile_triangle[idx].x1;
//t_idx.barrier.wait();
}
//t_idx.barrier.wait();
}
volume[t_idx.global] = sum;
}
);
acc_view.wait();
finish = clock();
copy(volume, volumeCPP.begin());
于是,每一个作品都落了下来。但有趣的是。它比 CPU(单核)代码成本更高。
CPU(单核)上的 C++ 需要 0.085 秒才能完成 1024 * 1024 * 2 个三角形的计算。但 AMP C++ 代码花费 0.530 秒。远远超过 C++ 代码。
在网上搜索后,有一个提示:如果我们先预热设备,我们可以在计算上得到“真实”的时间成本。
所以我先计算 128 个三角形来预热设备(耗时约 0.2 秒),然后通过计算 1024 * 1024 * 2 个三角形得到体积。它变得更快(花费大约 0.091 秒),但仍然比 CPU(单核)代码慢。
我想知道为什么,谁能帮助我加快计算。
非常感谢。
最佳答案
首先,下面是我认为稍微好一些的实现,并附有一些评论。您的代码正在做一些可以避免的事情。
然而,你在这里真正做的是减少。这是一种经过大量研究和优化的算法。 AMP Algorithms Codeplex site 上有一个 C++ AMP 实现它是作为 STL 风格的算法实现的。在得出 C++ AMP 不能满足您的需求的结论之前,我会尝试使用这个 reduce 实现,因为它做起来很简单,并且可能会给您带来更好的性能。我很想看看你过得怎么样。
AMP Book Codeplex site包含用于计时 C++ AMP 内核的辅助类。随附的书还讨论了实现减少。它有一整章。
void Foo()
{
const int numTriangles = 128;
std::vector<Triangle> vTriangle;
accelerator my_accelerator(accelerator::default_accelerator);
accelerator_view acc_view = my_accelerator.get_default_view();
const int BLOCK_SIZE = 64;
int outputSize = int(numTriangles / BLOCK_SIZE);
const int dimA = numTriangles;
std::cout<<dimA<<std::endl;
//copy triangles from host to device
// Use and array_view to automatically sync your data.
// You can use acc_view.flush() to make sure that copy is complete
// when you are running your timing code. Make this const so that AMP does
// not copy your input data back to the CPU.
array_view<const Triangle, 1> triangle(vTriangle.size(), vTriangle.data());
//Volume
// Don't push_back this causes (re)allocation as the vector grows.
// Set size and fill at the same time.
std::vector<double> volumeCPP(outputSize, 0.0);
array_view<double, 1> volume(outputSize, volumeCPP);
volume.discard_data();
// I would use the timing code on CodePlex.
// It will be more accurate than this.
clock_t start, finish;
start = clock();
parallel_for_each(
// Not sure a tile size of 1 will be handled that
// well by the runtime in terms of perf. I see why you
// are doing it to get tile_static. You might be better off having larger tiles.
volume.extent.tile<1>(),
[=](tiled_index<1> t_idx) restrict(amp)
{
double sum = 0.0f;
for (int idx = 0; idx < BLOCK_SIZE; idx++)
{
// Loading the single triangle into tiled memory is a good idea because
// elements are read more than once.
tile_static Triangle tile_triangle;
tile_triangle = triangle[t_idx.global * BLOCK_SIZE + idx];
sum += tile_triangle.x1 * tile_triangle.y2 * tile_triangle.z3 +
tile_triangle.y1 * tile_triangle.z2 * tile_triangle.x3 +
tile_triangle.x2 * tile_triangle.y3 * tile_triangle.z1 -
tile_triangle.x3 * tile_triangle.y2 * tile_triangle.z1 -
tile_triangle.x2 * tile_triangle.y1 * tile_triangle.z3 -
tile_triangle.y3 * tile_triangle.z2 * tile_triangle.x1;
}
volume[t_idx.global] = sum;
}
);
// Force data copy back to CPU.
volume.synchronize();
double sum = std::accumulate(begin(volumeCPP), end(volumeCPP), 0.0);
}
下面是另一个示例,它使用 AMP 算法库通过映射/归约模式实现了您的问题的解决方案。
std::vector<Triangle> triangles_cpu(1000);
array_view<const Triangle, 1> triangles_gpu(triangles_cpu.size(), triangles_cpu.data());
concurrency::array<double, 1> volumes_gpu(triangles_cpu.size());
array_view<double, 1> volumes_gpuvw(volumes_gpu);
amp_stl_algorithms::transform(begin(triangles_gpu), end(triangles_gpu), begin(volumes_gpuvw),
[=](const triangle& t) restrict(amp)
{
return t.x1 * (t.y2 * t.z3 - t.y3 * t.z2)
+ t.y1 * (t.z2 * t.x3 - t.x2 * t.z3)
+ t.z1 * (t.x2 * t.y3 - t.x3 * t.y2);
});
double sum = amp_stl_algorithms::reduce(begin(volumes_gpuvw), end(volumes_gpuvw), 0.0);
关于c++ - AMP C++ 加速体积计算,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18586804/
我正在关注 this关于在自己的网站中集成 Paypal 的教程。 例如,在页面中的第 3 步的第 20 行,我发现了这个: if (!isset($_POST["txn_id"]) &
amp-story 是否与 amp-access(或 amp-subscription)一起使用? 这里是 amp-access 的示例代码 { "authorization": "
我在一个主题中有几个非 AMP 页面。我的非 AMP 页面将在文章正文中包含指向同一主题中其他非 AMP 页面的链接。页面的 AMP 版本应该链接到同一主题中的其他 AMP 页面,还是文章中的所有链接
这是我正在尝试做的事情: 使用 google API 对邮政编码或城市和州进行地理定位。地址参数的值来自表单字段。 将地理线插入同一表单中的隐藏字段 提交表格。 我已经尝试使用 AMP-LIST 和
搜索控制台添加了一系列“引用的 AMP 网址不是 AMP”问题。 如果我使用 AMP Test我得到: 但是,当我 checkin https://validator.ampproject.org/时
更具体地说,您可以在未通过 AMP 验证的页面上使用 AMP 标记和代码吗? 用例:我想使我的网站完全使用 AMP,为此,我需要使用类似 on='tap:' 的东西对于我的下拉菜单和 用于跟踪,但我网
更具体地说,您可以在未通过 AMP 验证的页面上使用 AMP 标记和代码吗? 用例:我想使我的网站完全使用 AMP,为此,我需要使用类似 on='tap:' 的东西对于我的下拉菜单和 用于跟踪,但我网
如何使用 amp-list、amp-mustache、amp-form 和 amp-bind 实现自动建议? 想要为页内搜索实现自动建议 研究过这个Google example 希望autosugge
我想知道如何根据用户选择的选项获取文本内容并将其设置为amp-state。例如,如果用户选择“红色”选项。我想将“胭脂”设置为 amp-state 而不是“红色”。我知道我可以通过 setState
示例:- Open Iframe in Lightbox 我还尝试从顶部操纵 iFrame 的位置 75% 或 600px,但它也不起作用。 AMP iFr
我有一个名为 currentItem 的状态,其中包含 url、标题、描述...当我按下按钮时,currentItem 应保存在名为 myItems 的其他状态中。它将包含一个项目对象列表。 现在的问
我是 Azure SQL 数据库的新手(之前没有数据库经验),目前正在尝试从 microsoft learn 获得学位。我被困在这节课中,似乎无法弄清楚,但我认为这很容易。问题: PS /home/s
我正在尝试测试新的 amp-script 功能有多强大。但是,我收到此错误: Experiment "amp-script" is not enabled. log.js:187 "E
我在 AMP 结合 amp-state 和 amp-position-observe 时遇到问题。 { "visible": "n"
有 3 种方法可以将 AMP 与 PWA 结合起来(如 here 中所述): 具有 PWA 功能的 AMP 页面 AMP 作为 PWA 的入口点 AMP 作为 PWA 的数据源 在第一种和第三种方法中
我在 AMP 结合 amp-state 和 amp-position-observe 时遇到问题。 { "visible": "n"
我有一个 amp 故事,我需要从动态生成的 url 创建一个包含全屏视频的页面。在下面的第 2 页中,我直接使用 amp-video 组件呈现全屏,在第 3 页中,我使用 amp-list 提供视频
查看 AMP 规范,鉴于自定义样式元素依赖于 CSS 变量,这意味着当前的浏览器支持范围很窄。见:Can I use reference 我猜非自定义样式有一个“优雅的回退”,因为不理解 CSS 变量
我是 AMP 的新手。我有一个响应式网站,我需要在其主页上实现 AMP。是否可以使其与 AMP 兼容而不影响桌面 View ?或者我需要为 AMP 重写单独的代码? 最佳答案 您可以使用@media来
我在实现 amp-iframe 时在控制台中收到以下验证错误: Overflow element must be defined for resizable frames 有什么解决办法吗? 最佳答
我是一名优秀的程序员,十分优秀!