SIMD

一个指令,多个数据(SIMD)是一种“数据并行机制”形式,与Web Worker的“任务并行机制”相对应,因为他强调的不是程序逻辑的块儿被并行化,而是多个字节的数据被并行地处理。

使用SIMD,线程不提供并行机制。相反,现代CPU用数字的“向量”提供SIMD能力——想想:指定类型的数组——还有可以在所有这些数字上并行操作的指令;这些是利用底层操作的指令级别的并行机制。

使SIMD能力包含在JavaScript中的努力主要是由Intel带头的(https://01.org/node/1495),名义上是Mohammad Haghighat(在本书写作的时候),与Firefox和Chrome团队合作。SIMD处于早期标准化阶段,而且很有可能被加入未来版本的JavaScript中,很可能在ES7的时间框架内。

SIMD JavaScript提议向JS代码暴露短向量类型与API,它们在SIMD可用的系统中将操作直接映射为CPU指令的等价物,同时在非SIMD系统中退回到非并行化操作的“shim”。

对于数据密集型的应用程序(信号分析,对图形的矩阵操作等等)来说,这种并行数学处理在性能上的优势是十分明显的!

在本书写作时,SIMD API的早期提案形式看起来像这样:

  1. var v1 = SIMD.float32x4( 3.14159, 21.0, 32.3, 55.55 );
  2. var v2 = SIMD.float32x4( 2.1, 3.2, 4.3, 5.4 );
  3. var v3 = SIMD.int32x4( 10, 101, 1001, 10001 );
  4. var v4 = SIMD.int32x4( 10, 20, 30, 40 );
  5. SIMD.float32x4.mul( v1, v2 ); // [ 6.597339, 67.2, 138.89, 299.97 ]
  6. SIMD.int32x4.add( v3, v4 ); // [ 20, 121, 1031, 10041 ]

这里展示了两种不同的向量数据类型,32位浮点数和32位整数。你可以看到这些向量正好被设置为4个32位元素,这与大多数CPU中可用的SIMD向量的大小(128位)相匹配。在未来我们看到一个x8(或更大!)版本的这些API也是可能的。

除了mul()add(),许多其他操作也很可能被加入,比如sub()div()abs()neg()sqrt()reciprocal()reciprocalSqrt() (算数运算),shuffle()(重拍向量元素),and()or()xor()not()(逻辑运算),equal()greaterThan()lessThan() (比较运算),shiftLeft()shiftRightLogical()shiftRightArithmetic()(轮换),fromFloat32x4(),和fromInt32x4()(变换)。

注意: 这里有一个SIMD功能的官方“填补”(很有希望,预期的,着眼未来的填补)(https://github.com/johnmccutchan/ecmascript_simd ),它描述了许多比我们在这一节中没有讲到的许多计划中的SIMD功能。