为什么比NPOT图像更快地绘制POT图像?

时间:2013-06-14 03:32:44

标签: javascript performance canvas

我正在调查画布速度优化,我找到了这个答案:https://stackoverflow.com/a/7682200/999400

  
      
  • 不要使用奇数宽度的图像。始终使用宽度作为2的幂。
  •   

所以我想知道,为什么这会更快?

我看到的帖子解释说这有助于旧显卡(当使用OpenGL等时),但我说的是速度,而不是兼容性,还有画布,而不是OpenGL / WebGL。

1 个答案:

答案 0 :(得分:1)

它更快,因为你可以使用<<运算符而不是* oprator。即,执行“左移1”(乘以2)比执行“多次乘43”更快。可以通过在图像的每一行的末尾添加填充字节来解决这个限制(正如MS在内存位图中所做的那样),但实际上,这是两条指令之间速度差异的结果。

在8bit 320x200(模式13h)的旧时代,您可以使用简单的公式索引像素:

pixOffset = xPos + yPos * 320;

但这是懒散的。一个更好的选择是使用

<强> C

pixOffset = xPos + (yPos * 256) + (yPos * 64)

<强> ASM

mov ax, xPos    ;   ax = xPos
mov bx, yPos    ;   bx = yPos
shl bx, 6       ;   bx = yPos * 64
add ax, bx      ;   ax = xPos + (yPos * 64)
shl bx, 2       ;   bx = yPos * 256
add ax, bx      ;   ax = xPos + yPos * 320

这看似违反直觉,但写得不错时,它只使用单时钟指令。即您可以在6个时钟周期内计算偏移量。当然,流水线操作和缓存未命中会使场景复杂化。

在$$和晶体管中,实现硬件中的移位寄存器比完全乘法单元便宜得多。因此,可以使用相同数量的晶体管来提供更好的性能,或者可以在更低的功耗下使用更少的晶体管来实现相同的性能。

AFAIK,现代处理器的mul(和div)指令是在查找表的帮助下实现的。这在很大程度上缓解了这个问题,但也不是没有它的问题。如需进一步阅读,请查看Pentium fdiv错误(芯片内部有一个错误填充的查找表)

http://en.wikipedia.org/wiki/Pentium_FDIV_bug

所以最后,它实际上是用于实现功能的硬件/软件的人工制品。