原型对象不可清空,需清理的是其上不当共享的临时数据;应切断引用链、将可变状态移至实例层,用WeakMap管理缓存,显式解绑全局资源,并通过备份恢复被覆盖的原型方法。

原型对象本身不能也不该被“清空”,它不是缓存容器,真正需要清理的是挂在原型上、本不该共享的临时数据或引用。恢复初始状态的关键,是切断那些阻碍垃圾回收的引用链,并把可变状态移回实例层。
避免在 prototype 上存缓存数据
原型是所有实例共享的,直接挂数组、对象或 DOM 引用,会导致多个实例互相干扰,且数据长期驻留内存:
- ❌ 错误:所有实例共用一个 cache 数组,push 后彼此可见,且无法自动释放
Person.prototype.cache = {}; - ✅ 正确:缓存逻辑由实例自己管理,或使用 WeakMap 关联实例与缓存值
this.cache = new Map(); // 构造函数内初始化
用 WeakMap 管理实例级缓存
当确实需要缓存(如计算结果、格式化内容),WeakMap 是安全选择——它只持弱引用,实例被销毁时缓存自动失效:
- 定义缓存映射:
const cacheMap = new WeakMap(); - 写入:
cacheMap.set(this, expensiveResult); - 读取:
const cached = cacheMap.get(this); - 无需手动清空,也不影响 GC
主动清理原型上注册的全局资源
如果原型方法中绑定了 window 事件、定时器或 fetch 控制器,这些必须显式解绑才能释放:
- 注册时保存 ID 或引用:
this.resizeTimer = setTimeout(...); - 提供清理方法:
destroy() { clearTimeout(this.resizeTimer); this.resizeTimer = null; } - 不把 timer、AbortController 等挂到 prototype 上——那是实例生命周期的事
恢复原型方法本身(非缓存)
若你曾覆盖了原型方法(比如重写了 toString),想还原原始行为,只需恢复原方法引用:
- 提前备份:
const originalToString = Date.prototype.toString; - 覆盖后恢复:
Date.prototype.toString = originalToString; - 或删除自定义方法:
delete Date.prototype.toString;(仅对自有属性有效)











