【问题标题】:modulo operation vectorization模运算矢量化
【发布时间】:2013-09-24 10:16:18
【问题描述】:

有一个循环:

 long a* = new long[32];
 long b* = new long[32];
 double c* = new double[32];
 double d = 3.14159268;
  //set a, b and c arrays
  //.....
  for(int i = 0; i < 32; i ++){
    d+= (a[i] % b[i])/c[i];
  }

我如何使用英特尔 C++ 向量化功能(例如 #pragma simd 或 sse- 指令)来实现这个循环?

如果我写:

  #pragma simd reduction(+:c)
  for(int i = 0; i < 32; i ++){
    d+= (a[i] % b[i])/c[i];
  }

然后速度不会增加:(

【问题讨论】:

  • 为什么要将结果投射到double
  • 该代码无法编译。也许你的意思是(double)(a[i] % b[i])
  • @us2012:这个结果必须是双倍的。示例更正为示范。
  • @interjay 是的,抱歉,示例已更正。
  • 您是否添加了适当的编译器开关?

标签: c intel vectorization


【解决方案1】:

Intel 64 和 IA-32 架构没有矢量化整数除法或余数/模指令,因此在使用整数运算时无法在硬件中对一般余数运算进行矢量化。

有一些浮点向量除法指令。在我检查过的处理器中,双精度除法 (DIVPD) 并未真正矢量化;它花费的时间是单精度除法的两倍,因此硬件通过串行使用一个除法器来实现它(甚至没有任何显着程度的流水线)。

如果单精度就足够了,您也许可以从使用单精度向量除法 (DIVPS) 中获得一些提升,但您必须处理浮点舍入并注意确保获得所需的结果.在 Newton-Raphson 中使用近似倒数指令 (RCPPS) 可能比使用 DIVPS 更快,但在设计中需要更加小心。

【讨论】:

    猜你喜欢
    • 2011-07-08
    • 2014-05-28
    • 2015-06-27
    • 1970-01-01
    • 2014-01-03
    • 1970-01-01
    • 2017-02-28
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多