【发布时间】:2016-12-05 22:19:05
【问题描述】:
假设我有一个stl::array<float, 24> foo,它是列主格式 arrayfire 数组的线性化 STL 挂件,例如af::array bar = af::array(4,3,2, 1, f32);。所以我有一个af::dim4 对象dims,其尺寸为bar,我有多达4 个af::seq-objects,我有线性化数组foo。
如何明确获得foo 的索引(即bar 的线性化版本),例如2.nd 和 3.rd 行,即bar(af::seq(1,2), af::span, af::span, af::span)?我在下面给出了一个小代码示例,它显示了我想要的。最后我也解释了为什么我想要这个。
af::dim4 bigDims = af::dim4(4,3,2);
stl::array<float, 24> foo; // Resides in RAM and is big
float* selBuffer_ptr; // Necessary for AF correct type autodetection
stl::vector<float> selBuffer;
// Load some data into foo
af::array selection; // Resides in VRAM and is small
af::seq selRows = af::seq(1,2);
af::seq selCols = af::seq(bigDims[1]); // Emulates af::span
af::seq selSlices = af::seq(bigDims[2]); // Emulates af::span
af::dim4 selDims = af::dim4(selRows.size, selCols.size, selSlices.size);
dim_t* linIndices;
// Magic functionality getting linear indices of the selection
// selRows x selCols x selSlices
// Assign all indexed elements to a consecutive memory region in selBuffer
// I know their positions within the full dataset, b/c I know the selection ranges.
selBuffer_ptr = static_cast<float> &(selBuffer[0]);
selection = af::array(selDims, selBuffer_ptr); // Copies just the selection to the device (e.g. GPU)
// Do sth. with selection and be happy
// I don't need to write back into the foo array.
Arrayfire 必须实现这样的逻辑才能访问元素,我发现了几个相关的类/函数,例如 af::index, af::seqToDims, af::gen_indexing, af::array::operator() - 但是我还想不出一个简单的方法。
我考虑过基本上重新实现operator(),以便它可以类似地工作,但不需要引用数组对象。但是,如果在 arrayfire 框架中有简单的方法,这可能是浪费精力。
背景:
我想这样做的原因是,arrayfire 不允许在与 GPU 后端链接时仅将数据存储在主内存(CPU 上下文)中。由于我有大量数据需要逐块处理,而且 VRAM 非常有限,我想从一个始终驻留在主内存中的 stl 容器临时实例化 af::array-objects 。
当然我知道我可以编写一些索引魔法来解决我的问题,但我想使用相当复杂的 af::seq 对象,这可能会使索引逻辑的有效实现变得复杂。
【问题讨论】:
-
为什么线性索引在这种情况下会有帮助?如果您可以在获得线性索引后显示一些有关您计划做什么的代码,那就太好了。
标签: c++ arrays stl matrix-indexing arrayfire