![[二进制数据.excalidraw]]

ArrayBuffer

ArrayBuffer 是用来表示通用的原始二进制数据缓冲区,本质是一个字节数组

const buffer = new ArrayBuffer(16) // 创建一个长度为 16 Byte 的 buffer
console.log(buffer.byteLength) // 16

注意:创建后长度固定,不可调整

它会分配一个 16 字节的连续内存空间,并用 0 进行预填充

ArrayBuffer 不是 Array

ArrayBuffer 是对固定长度的连续内存空间的引用,不同与 Array

ArrayBuffer 本身不能直接读写,需要借助数据视图:

类型化数组(TypedArray)

ArrayBuffer 是一个内存区域,它里面存储了什么无从判断,只是一个原始的字节序列。想要操作 ArrayBuffer,需要使用“视图”对象。视图对象本身并不存储任何东西,它是一副“眼镜”,透过它来解释存储在 ArrayBuffer 中的字节

![[Pasted image 20240817183421.png]]

类型化数组 每个元素所占字节数 描述(C 语言中的数据类型)
Int8Array 1 8 位整型数(signed char
UInt8Array 1 8 位无符号整型数(unsigned char
Uint8ClampedArray 1 8 位无符号整型数,溢出时有特殊处理
Int16Array 2 16 位整型数(signed short
UInt16Array 2 16 位无符号整型数(unsigned short
Int32Array 4 32 位整型数(signed int
UInt32Array 4 32 位无符号整型数(unsigned int
BigInt64Array 8 64 位整型数(signed long / long long
BigUint64Array 8 64 位整型数(unsigned long / long long
Float32Array 4 单精度 32 位浮点数(float
Float64Array 8 双精度 64 位浮点数(double

构造器

书写 TypedArray 的说明

没有名为 TypedArray 的构造器,它只是表示 ArrayBuffer 上的视图之一的通用总称术语

当你看到 new TypedArray 之类的内容时,它表示 new Int8Arraynew Uint8Array 及其他中之一

可以直接创建一个 TypedArray,而无需提及 ArrayBuffer。但是,视图离不开底层的 ArrayBuffer,因此,除第一种情况(已提供 ArrayBuffer)外,其他所有情况都会自动创建底层 ArrayBuffer

属性

如要访问底层的 ArrayBuffer,在 TypedArray 中有如下的属性:

其他属性:

方法 ^1

TypedArray 具有和 Array 相同的方法设计,可以设置获取元素(arr[i]setget)、查找(indexOflastIndexOf)、填充(fill)、切片(slice)、反转(reverse)、排序(sort)、拼接字符串(join)、遍历(forEachmapfindreduce )等

但没有 pushpopshiftunshiftspliceconcat 等会改变数组长度的方法

还有两种 Array 没有的方法:

溢出处理

如果尝试将越界值写入类型化数组,多余的高位数据将会被忽略

如尝试将 256 放入 Uint8Array,则超出的最高位的 1 会被忽略,因此结果是 0:

![[Pasted image 20240817175322.png]]

Uint8ClampedArray 在这方面比较特殊,它的表现不太一样。对于大于 255 的任何数字,它将保存为 255,对于任何负数,它将保存为 0。此行为对于图像或颜色处理很有用

数据视图(DataView)

类型化数组限制了数据每个元素的字节大小,而 DataView 是在 ArrayBuffer 上的一种超灵活的“未类型化”视图,它允许以任何格式访问任何偏移量(offset)的数据

构造器

DataView 与类型化数组不同,只有这一个构造器,即 DataView 不会自行创建缓冲区,需要事先准备好

属性

方法

没有与 ArrayTypedArray [[#^1|相类型的方法]],只有对不同偏移量读写的方法:

字节序

字节序或字节顺序描述了计算机如何组织构成数字的字节

例如,用不同字节序存储数字 0x12345678

Blob

Blob 全称 Binary Large Object,表示一个不可变的原始数据块,支持文本和二进制数据

特点:

创建方式:

const blob = new Blob(
  ["Hello World"],
  { type: "text/plain" }
);

切片操作:

const slicedBlob = blob.slice(0, 5, "text/plain");

核心功能与应用场景

功能 说明
分片上传 .slice(start, end) 方法可用于大文件切片上传
本地预览 canvas.toBlob() 导出图像,配合 URL.createObjectURL 预览
文件下载 使用 a 标签 + createObjectURL 实现无刷新下载
缓存资源 Service Worker 中缓存 Blob 数据提升性能
处理用户上传 结合 FileReader 和 File API 操作用户文件

File

[[004.浏览器离线存储#File API|File API]]

File 对象继承自 Blob,额外包含:文件名 name ,最后修改时间 lastModified ,可以理解为:带有元数据的 Blob

创建方式:

const file = new File(
  ["Hello World"],
  "example.txt",
  { type: "text/plain" }
);

获取方式

一般通过用户上传的文件获取

示例:

// <input type="file">

const input = document.getElementById("input");
input.onchange = (event) => {
  const files = event.target.files;
  console.log("Files:", files); // FileList
};

FileReader

FileReader 是一个用于异步读取 Blob 或 File 内容的接口

常用实例方法

方法 说明
readAsArrayBuffer() 读取为 ArrayBuffer,适合二进制
readAsText() 读取为字符串
readAsDataURL() 读取为 Base64 编码

常用属性

示例:读取 Blob 并输出文本

let blob = new Blob(["Hello World!"], { type: "text/plain" });
blob = blob.slice(0, 5, "text/plain");

const fileReader = new FileReader();
fileReader.readAsText(blob);
fileReader.onload = function() {
  console.log(fileReader.result); // Hello
};

ObjectURL

ObjectURL 用于为 Blob 或 File 对象生成一个临时 URL,可直接在 <img><a>iframe 等 标签中使用

示例:文件选择并预览

const input = document.getElementById("input");
const image = document.getElementById("image");

input.onchange = (event) => {
  const file = event.target.files[0];
  const url = URL.createObjectURL(file);
  image.src = url;
};