作為一個前端同學我們跨過了只關注實現(xiàn)業(yè)務功能的階段后,會進入一個瓶頸豌熄。在這個瓶頸階段,我們需要通過更多的知識實踐來積累物咳,讓我們跨過這段平臺期锣险。前端架構、框架原理、性能優(yōu)化等都是我們需要取掌握的技能囱持。本章節(jié)就從性能優(yōu)化的一個角度----JavaScript性能優(yōu)化 進化吧夯接!
內存管理
如果我們在日常的編程中不注意管理內存,會導致內存泄露, 產(chǎn)生瀏覽器崩潰等情況纷妆。
內存管理: 開發(fā)者主動申請盔几、使用、釋放內存空間
//申請
let obj = {}
//使用
obj.name = "zicoo"
//釋放
obj = null
JavaScript 中的垃圾回收
- JavaScript中內存管理是自動的
- 對象不再被引用時是垃圾
- 對象不能從根上訪問到時是垃圾
可達對象
- 可以訪問到的對象就是可達對象(引用掩幢、作用域鏈)
- 可達的標準是從根觸發(fā)是否能夠被找到
- javascirpt 中的根可以理解為全局變量對象
引用與可達
let obj = {name: "sam"}
let obj1 = obj
obj = null //obj 仍然可達
GC - 垃圾回收機制
- GC是一種機制逊拍,垃圾回收器完成具體的工作
- 工作的內容是查找垃圾釋放空間、回收空間
- 算法就是工作中查找和回收所遵循的規(guī)則
常見GC算法
- 引用計數(shù)
- 標記清除
- 標記整理
- 分代回收
引用計數(shù)
核心思想: 設置引用計數(shù)器际邻,判斷當前引用數(shù)為否為0
優(yōu)點:
- 發(fā)現(xiàn)垃圾立即回收
- 最大限度減少程序暫停
缺點:
- 無法回收循環(huán)引用的對象
- 時間開銷大
function fn() {
const obj1 = {}
const obj2 = {}
obj1.name = obj2
obj2.name = obj1 //obj1 obj2 循環(huán)引用 無法將引用計數(shù)器清0
}
fn()
標記清除
核心思想: 分標記和清除兩個階段
- 遍歷所有對象找到標記活動對象
- 遍歷所有對象清除沒有標記的對象
- 回收相應的空間
執(zhí)行時間點: 當有效內存空間被耗盡的時候芯丧,會停止程序執(zhí)行標記清除
標記活動對象依舊是從根出發(fā),遞歸的方式遍歷從根能到達的所有節(jié)點世曾,并且標記為活動對象缨恒, 而未標記活動對象的節(jié)點則就是待回收節(jié)點
優(yōu)點:
- 對于循環(huán)引用的對象可以被回收,可以彌補引用計數(shù)的缺點
缺點:
- 由于內存空間申請的時候是有序申請轮听,但是回收的時候節(jié)省的內存空間信息是不會整合的骗露,導致節(jié)省的內存空間不連續(xù),從而造成空間碎片化
標記整理
- 標記整理算法是標記清除的增強
- 標記階段的操作和標記清除一致
- 清除階段會先執(zhí)行整理血巍,移動對象位置萧锉, 使時間碎片連續(xù)
V8引擎
- 主流的JavaScript執(zhí)行引擎
- V8采用即時編譯
- V8內存設限 (64位系統(tǒng)不超過 1.5G 21位系統(tǒng)不超過800M)
V8垃圾回收策略
- 采用分代回收的思想
- 內存分為新生代、老聲帶
- 針對不同的對象采用不同算法
V8常見GC算法
- 分代回收
- 空間復制
- 標記清除
- 標記整理
- 標記增量
V8 新生代對象回收
- V8 內存空間一分為二
- 小空間用于存儲新生代對象(64位32M | 32位16M)
- 新生代對象指存活時間較短的對象
例如:局部作用域的變量是新生代述寡, 全局變量存是老年代
新生代對象回收實現(xiàn)
- 回收過程采用復制算法 + 標記整理
- 新生代內存區(qū)分為兩個等大空間
- 使用空間為From 狀態(tài)柿隙, 空閑空間為 To狀態(tài)
- 活動對象存于From 空間
- 等到回收階段,標記整理后會將活動對象拷貝到To
- 釋放掉From
細節(jié)說明 - 拷貝過程中可能出現(xiàn)晉升
- 晉升就是將新生代對象移動至老年代
- 一輪GC還存活的新生代需要晉升
- To 空間使用率超過25%,之后拷貝的對象則會晉升
V8 老年代對象回收
- 老年代64位操作系統(tǒng)1.4G ,32位操作系統(tǒng)700m
- 老年代活動對象指存活時間較長的對象
老年代對象回收實現(xiàn)
- 主要采用標記清除鲫凶、標記整理禀崖、增量標記算法
- 首先使用標記清除完成垃圾空間的回收(存在空間碎片)
- 采用標記整理進行空間優(yōu)化(新生代晉升時,老年代區(qū)域不足以存放新生代對象)
- 采用增量標記進行效率優(yōu)化
增量標記
程序執(zhí)行與標記間隔執(zhí)行螟炫,達到清理標準一起清理
細節(jié)對比
- 新生代區(qū)域垃圾回收使用空間換時間
- 老年代區(qū)域垃圾回收空間大波附,不適合復制算法