DataView 中 字节序

DataView 视图是一个可以从 二进制ArrayBuffer 对象中读写多种数值类型的底层接口,使用它时,不用考虑不同平台的字节序问题。
DataView 下面的很多方法可以操作字节序的方式,以 getInt16 为例

dataview.getInt16(byteOffset [, littleEndian])

参数
byteOffset
偏移量, 单位为字节, 从头开始计算.
littleEndian
可选 表示该 16 位整数是否以 little- or big-endian 格式存储的(就是使用的字节序格式,具体参考链接页面);如果传入的值为 true,就表示使用 little-endian(低字节序),如果传入的值为 false 或者 undefined,则会使用 big-endian(高字节序) 方式读值。

字节序

当数据太大,一个字节存不下的时候,我们就得使用多个字节了。比如,我有个需要4个字节存储的整数,为了方便说明,使用16进制表示这个数,例如0x12345678。有的人采用以下方式存储这个个数字:
DataView 中 字节序_第1张图片

这个方案看起来不错,但是,又有人采用了以下方式:
DataView 中 字节序_第2张图片

两种方案虽有不同,但也有共识,即依次存储每一个数字,即0x12345678。大家的分歧在于,对于某一个要表示的值,因为只能一个字节一个字节的存,我是把值的低位存到低地址,还是把值的高位存到低地址。前者使用的是“小端(Little endian)”字节序,即先存低位的那一端(数字的最低位是0x78),如上图中的第一个图;后者使用的是“大端(Big endian)”字节序,即先存高位的那一端(数字的最高位分是0x12),如上图中的第二个图。

由此也引发了计算机界的大端与小端之争,不同的CPU厂商并没有达成一致:

x86,MOS Technology 6502,Z80,VAX,PDP-11等处理器为Little endian。
Motorola 6800,Motorola 68000,PowerPC 970,System/370,SPARC(除V9外)等处理器为Big endian。
ARM, PowerPC (除PowerPC 970外), DEC Alpha, SPARC V9, MIPS, PA-RISC and IA64的字节序是可配置的。

示例代码(node)

const { Buffer } = require('buffer')

const buf = Buffer.from([0x12, 0x34, 0x56, 0x78])

function toArrayBuffer(buf) {
  var ab = new ArrayBuffer(buf.length);
  var view = new Uint8Array(ab);
  for (var i = 0; i < buf.length; ++i) {
      view[i] = buf[i];
  }
  return ab;
}

const arrayb = toArrayBuffer(buf)

const view = new DataView(arrayb)

console.log(view.getInt16(0)) // 4660 -> 0x1234
console.log(view.getInt16(0, true)) // 13330 -> 0x3412

参考:
https://zhuanlan.zhihu.com/p/...
https://developer.mozilla.org...

你可能感兴趣的:(前端node.js)