JS - 引用类型思维导图 & String 的一些 bug 解决偏方

192 阅读2分钟

引用值(或对象)是某个特定引用类型的实例,引用类型就是把数据和功能组织在一起的结构,引用类型虽然有点像类,但是和类不是一个概念

Date

RegExp 正则

// 匹配字符串中的所有 "at";
const p1 = /at/g;
log(p1.test("that")); // true;

// 匹配第一个不区分大小写的 "bat" or "cat"
const p2 = /[bc]at/i;
log(p2.test("BAT")); // true;
log(p2.test("baT")); // true;

// 匹配所有包含 "at" 的三个字符组,忽略大小写
const p3 = /.at/gi;

log(p3.test("nat3")); // true
log(p3.test("at3")); // false

原始值和包装类型

扩展 Unicode 增补平面的问题

/**
 * 字符在 Unicode 增补字符平面时.length, charAt(index)等方法就会出现问题,
 * 因为 16 位只能唯一表示 Math.pow(2,16) = 65536 个字符
 */
const msg = "ab😊de";
log(msg.length); // 6 不是预期的5,因为 😊 占了不是基于 16位码元完成的
log(msg.charAt(1)); // log: "b",预期一样
log(msg.charAt(2)); // log: "�" 预期不一样
log(msg.charAt(3)); // log: "�" 预期不一样
log(msg.charAt(4)); // log "d" 预期一样

log(String.fromCharCode(97, 98, 55357, 56842, 100, 101)); // 该方法正常

str.normalize(NFx) 实现字符串的标准化 解决一些 bug

// 不同的编码对应同一个字符(如下的 几个 编码都对应 "Å",但是他们却互不相等)
const a1 = String.fromCharCode(0x00c5),
  a2 = String.fromCharCode(0x212b),
  a3 = String.fromCharCode(0x0041, 0x030a);
log(a1, a2, a3); // Å Å Å
// 但是他们互不相等,因为编码方式不同
log(a1 == a2 || a1 == a3 || a2 == a3); // false

/**
 * 同一个字符可以有不同的编码方式,但是因为编码不同导致出现相同的字符却不相等
 * 为了解决这个 bug: Unicode 提供了 4 中规范化形式: NFD、NFKD、NFC、NFKC
 * 可以选择同一种规范话形式可以让比较仓做符返回正确的结果
 */
const normalizeNFD = (str) => str.normalize("NFD");
log(
  normalizeNFD(a1) === normalizeNFD(a2) ||
    normalizeNFD(a1) === normalizeNFD(a3) ||
    normalizeNFD(a2) === normalizeNFD(a2)
); // true