我第一次使用Accelerate框架,目标是将一些矢量化代码实现到iOS应用程序中。我从未尝试过在Objective C或C中使用向量方面做任何事情。有了一些MATLAB的经验,我想知道使用Accelerate确实是更多的痛苦。假设我想要计算以下内容:
b = 4*(sin(a/2))^2
其中a和b是向量。
MATLAB代码:
a = 1:4;
b = 4*(sin(a/2)).^2;
然而,正如我在通过文档进行一些随地吐痰之后所看到的那样,使用Accelerate的情况完全不同。
我的C实现:
float a[4] = {1,2,3,4}; //define a
int len = 4;
float div = 2; //define 2
float a2[len]; //define intermediate result 1
vDSP_vsdiv(a, 1, &div, a2, 1, len); //divide
float sinResult[len]; //define intermediate result 2
vvsinf(sinResult, a2, &len); //take sine
float sqResult[len]; //square the result
vDSP_vsq(sinResult, 1, sqResult, 1, len); //take square
float factor = 4; //multiply all this by four
float b[len]; //define answer vector
vDSP_vsmul(sqResult, 1, &factor, b, 1, len); //multiply
//unset all variables I didn't actually need
老实说,我不知道这里最糟糕的是:跟踪所有中间步骤,试图记住参数在vDSP中如何传递VecLib(完全不同),或者需要花费很多时间做一些事情微不足道的。
我真的希望我在这里遗漏了一些东西,大多数步骤都可以合并或缩短。任何关于编码资源,良好的编码习惯(从困难的方式或从书中学习)等的建议都将非常受欢迎!你们如何处理多行矢量计算?
答案 0 :(得分:1)
我想你可以这样写,但对我来说似乎非常复杂。我更喜欢这个(特定于英特尔,但可以很容易地为其他架构抽象):
#include <Accelerate/Accelerate.h>
#include <immintrin.h>
const __m128 a = {1,2,3,4};
const __m128 sina2 = vsinf(a*_mm_set1_ps(0.5));
const __m128 b = _mm_set1_ps(4)*sina2*sina2;
另外,只是为了迂腐,你在这里做的不是线性代数。 线性代数仅涉及线性运算(没有平方,没有像sin
那样的超越运算。)
编辑:正如您所指出的,上面的内容在iOS上并不能完全开箱即用;最大的问题是没有vsinf
(iOS上的Accelerate中没有vMathLib)。我没有在我的机器上安装SDK进行测试,但我相信以下内容应该有效:
#include <Accelerate/Accelerate.h>
const vFloat a = {1, 2, 3, 4};
const vFloat a2 = a*(vFloat){0.5,0.5,0.5,0.5};
const int n = 4;
vFloat sina2;
vvsinf((float *)&sina2, (const float *)&a, &n);
const vFloat b = sina2*sina2*(vFloat){4,4,4,4};
不像vMathLib那样漂亮,但仍然相当紧凑。
一般来说,对矢量的许多基本算术运算起作用;没有必要使用对任何库的调用,这就是为什么Accelerate不会干净利落地提供这些操作的原因。相反,Accelerate通常会尝试提供其他方式无法立即提供的操作。
答案 1 :(得分:0)
回答我自己的问题: 在iOS 6中,将引入vMathLib。正如Stephen澄清的那样,vMathLib已经可以在OSX上使用,但它在iOS中不可用。到现在为止。
vMathLib提供的功能将允许更容易的矢量计算。