对象字面量

const user = {
    name: 'Alice',
    age: 30,
    sayHi() {
        return `Hi, ${this.name}`;
    },
    get description() {
        return `${this.name} (${this.age})`;
    },
};

user.name              // 'Alice'
user['age']            // 30
user.sayHi()           // 'Hi, Alice'
user.description       // 'Alice (30)'(getter,不用加 ())

简写语法

const name = 'Alice';
const age = 30;

// 字段简写
const user = { name, age };          // 等同 { name: name, age: age }

// 方法简写
const user2 = {
    greet() { ... }                  // 等同 greet: function () { ... }
};

// 计算属性名
const key = 'dynamicKey';
const obj = { [key]: 'value' };      // { dynamicKey: 'value' }

展开 / 解构

const a = { x: 1, y: 2 };
const b = { ...a, z: 3 };            // { x: 1, y: 2, z: 3 }
const c = { ...a, x: 10 };           // { x: 10, y: 2 }   后者覆盖

// 解构
const { x, y } = a;
const { x: newX, y = 999 } = a;      // 改名 + 默认值
const { x, ...rest } = b;            // x=1, rest={y:2,z:3}

class 语法

class User {
    constructor(name, age) {
        this.name = name;
        this.age = age;
    }

    sayHi() {
        return `Hi, ${this.name}`;
    }

    static createGuest() {
        return new User('Guest', 0);
    }

    get description() {
        return `${this.name} (${this.age})`;
    }

    set description(value) {
        // ...
    }
}

const u = new User('Alice', 30);
u.sayHi();                           // 'Hi, Alice'

const guest = User.createGuest();    // static 方法

继承

class Admin extends User {
    constructor(name, age, role) {
        super(name, age);            // 必须先调 super
        this.role = role;
    }

    canDelete() {
        return this.role === 'super';
    }
}

const a = new Admin('Bob', 40, 'super');
a.sayHi();           // 继承 User 的方法
a.canDelete();       // true

私有字段(# 前缀)

class Counter {
    #count = 0;                       // 私有,外部不可访问

    increment() {
        this.#count++;
    }

    get value() {
        return this.#count;
    }
}

const c = new Counter();
c.increment();
c.value          // 1
c.#count         // ❌ SyntaxError

class vs 对象字面量怎么选

用对象字面量 用 class
简单数据载体 需要"创建多个实例"
静态配置 需要继承
单次使用 有共享方法
// 简单数据 → 对象
const config = { port: 8080, host: 'localhost' };

// 实例 → class
class Connection { ... }
const c1 = new Connection();
const c2 = new Connection();

原型链(最浅一层)

JS 的"继承"底层是原型链。class 是糖:

class Animal {}
class Dog extends Animal {}

const d = new Dog();
d.__proto__ === Dog.prototype                      // true
Dog.prototype.__proto__ === Animal.prototype       // true
Animal.prototype.__proto__ === Object.prototype    // true

写应用代码不用关心原型链——会用 class 和对象字面量够了。

对象常用工具方法

Object.keys(obj)                     // 所有 key
Object.values(obj)                   // 所有 value
Object.entries(obj)                  // [[key, val], ...]
Object.fromEntries([['a', 1]])       // { a: 1 }(entries 的反操作)
Object.assign({}, a, b)              // 合并(不变原对象)
Object.freeze(obj)                   // 冻结(不能改)
Object.is(NaN, NaN)                  // true(严格相等 + NaN 处理)
'key' in obj                          // 检查 key 存在
delete obj.key                        // 删 key

  • for in 会遍历继承的属性——用 Object.keys()for of Object.entries() 更稳
  • JSON.stringify 不会序列化函数 / undefined / Symbol——会安静丢
  • 比较两个对象永远是引用比较{} === {} 是 false)—— 深比较用 deepEqual 库或自己写
  • 私有字段 #x 是新语法(Node 12+)——老代码常见 _x 约定(弱私有)

下一篇:数组与迭代。