类型化数组(Typed Array)也是HTML5中新引入的API。用一句话解释类型化数组就是:它是JS操做二进制数据的接口。 众所周知,直接操做二进制数据可使程序更为高效, 尽管JS对常规数组作了不少优化(JS数组被实现为对象形式),可是不得不认可JS数组的效率一直不高。好比在WebGL中的图像数据传输, 若是使用原生的JS数组, 浏览器在与显卡通讯时,必须将它转换为二进制形式,这一步较为耗时。正是由于有大量二进制数据的操做需求,因此ArrayBuffer应运而生。在Canvas(可参考本人canvas笔记canvas的基本原理)中,使用getImageDate()
方法所返回的ImageData
对象就是一个类数组对象,HTML标准中称其为CanvasPixelArray
,它除了在值的处理方式上与ArrayBuffer
中视图类型Unit8Array
有点区别外,其余都同样(Unit8Array
只能处理0-255的数字,而CanvasPixelArray
能够处理更多)编程
对于刚接触类型化数组的概念看到这可能仍是云里雾里,下面将逐一将我所理解的ArrayBuffer中的关键概念作个整理:canvas
大多数资料中对于视图都是一句带过,好比这篇博客中(ArrayBuffer:类型化数组)对于视图的解释就是:segmentfault
ArrayBuffer做为内存区域,能够存放多种类型的数据。不一样数据有不一样的存储方式,这就叫作“视图”。数组
当我刚看到上面的解释,仍是没法体会“视图”的含义,暂且把ArrayBuffer的概念放一边, 想象一下,既然是操做二进制数据的接口,那么该如何操做他们呢, 好比8位二进制数1是00000001
,咱们确定不会使用原始的二进制编程,那么当咱们操做这个1
时,确定是以1
的形式操做, 那么这里的1
就是视图(view)了, 视图能够理解为方便理解的二进制数据。若是知道C语言,对于这个概念就不难把握了,好比C语言中的字符串实际是数字,那么这里的字符串也能够理解为“视图”。其实这里的视图就是类型化数组。浏览器
ArrayBuffer是一段不透明的内存区域(所谓不透明,就是没法直接操做的数据块),单位是字节(Byte)也就是8位,它的byteLength
属性返回其内存大小。在JS中,经过构造函数的形式申明一段ArrayBuffer区域:网络
var a = new ArrayBuffer(10) a.byteLength // =>10
在这段内存区域上,可使用不一样的视图来建立任意数量的类型化数组, 这些类型化数组也能够是重叠的。有八种不一样的类型化数组(视图),分别为:架构
Int8Array:8位有符号整数,长度1个字节。函数
Uint8Array:8位无符号整数,长度1个字节。优化
Int16Array:16位有符号整数,长度2个字节。.net
Uint16Array:16位无符号整数,长度2个字节。
Int32Array:32位有符号整数,长度4个字节。
Uint32Array:32位无符号整数,长度4个字节。
Float32Array:32位浮点数,长度4个字节。
Float64Array:64位浮点数,长度8个字节。
这里引用这篇博客中(JavaScript中的ArrayBuffer详细介绍)的例子来解释ArrayBuffer区域中出现的重叠(也叫复合视图)现象:
var buffer = new ArrayBuffer(12) var x = new Float32Array(buffer, 0, 2) var y = new Float32Array(buffer, 4, 1) x[1] = 7; console.log(y[0]); // 7
原文中做者的解释过于简单。这里的y[0]
之因此为7,是由于在buffer
这段12个字节的内存区域中,申明来一个从0字节开始,长度为2的32位浮点数x
(也就是说x占了前8个字节),再申明一个从第4
个字节开始,长度为1的32位浮点数y
,那么这里的y
与x
实际上就是重叠的,x
已经占了8个字节,而y
是从第4个字节开始的。既然是重叠的,那么改变x
势必会影响到y
,这里x
类型化数组的第一个元素赋值为7,那么在ArrayBuffer中便是00000000 00000000 00000000 00000111
而y
是从第四个字节开始,也就是从00000111
开始, 因此y
也是00000111
也就是7了。
类型化数组实质上是二进制数据,而ArrayBuffer这段区域又是指定长度的,基于这些即可推出其与常规数组的区别:
类型化数组元素都是数字,它不像JS常规数组那样能够参杂不一样类型,好比下面例子?中的赋值就是无效的
类型化数组长度固定
全部元素初始化为0
var a = new Int8Array(3) a[0] = 'hello' a[0] // =>0 显示a[0]依然未定义 a[0] = '8' a[0] // = > 8 可是注意类型的自动转换,当可被转换成数字时,JS会自动将其转成数值
既然本质是在操做二进制数据,那么就涉及到“高位优先(big-endian)”仍是“低位优先(little-endian)”的数据传输问题,DataView的一整套API中就涉及到解决该问题,在当前的大部分CPU架构中的字节传输顺序都是使用低位优先,而在大部分的网络协议中使用的字节顺序倒是高位优先(好比HTTP协议),它的一系列get方法中就能够设置字节的处理顺序。DataView也是一种视图,它的原理并不难,详细的dataview的API能够看前面提到的博客中的DataView章节。mark?ArrayBuffer:类型化数组
二进制数据的接口主要应用于文件,在JS中涉及文件处理的API几乎均可以应用ArrayBuffer,主要是Ajax,File,Canvas。这几个例子等下再码,争取写出跟前面博客不同的东西,先搬砖……