JS、VUE內存溢出問題的解決方案
1、學會使用devTool
Memory詳解:
a、需要使用Memory來分析內存變化,至少記錄兩次內存快照,用于做內存變化比對。

舉例:
編輯器有內存溢出,所以在打開前記錄一次快照,打開編輯器等待加載完成,然后關閉編輯器,再記錄一次快照。
兩次快照間的內存差異,很大可能是內存溢出部分。當然,也有可能是一些依賴增長,此時多次打開關閉,觀察內存變化,持續累積的部分必然是內存溢出。
b、關注detachDomElement
detach的元素表示這些DOM元素不在DOM樹中,但是有被js對象所引用。
一般來說,這是內存溢出查找的主要入口。

查找的流程
1、找到shallow size較大的元素,一般來說會是HTMLDivElement,任意選中其中的一項,可以看到以下內容:

該清單表示它的被引用情況,此時,重點關注以下幾項:
1、用戶寫的對象
2、監聽
3、context上下文,上下文表示一些未被回收的函數中,有使用到相關對象
2、常見的解決方案
1 監聽的問題
很多開發者在使用觀察者模式后,忘了寫對應的注銷代碼,這是大忌。不論是js、jquery、vue還是自己寫的監聽,都必須有對應的注銷代碼。
有on就得有off。
有addListener就得有removeListener。
舉例:
在mounted的時候注冊的監聽,在beforeDestroy時候銷毀。

2、VUE本身的問題
VUE掛載了大量的對象,有可能因為用戶代碼的介入,導致無法銷毀,所以加入以下代碼:
const cleanVnode=vnode=>{
if(vnode){
vnode.elm = null;
vnode._renderChildren=null;
vnode.children=null;
// vnode.context=null;
vnode.componentOptions=null;
}
}
Vue.mixin({
beforeDestroy() {
if(this.$el)
delete this.$el.__vue__;
},
destroyed() {
//為了內存,清空所有內容
this.$children = [];
this.$parent = null;
this._watchers = [];
this.$refs = {};
this.$root = null;
this.$slots = [];
this.$store = null;
cleanVnode(this._vnode);
cleanVnode(this.$vnode)
this._vnode = null;
this.$vnode = null;
if(this.$el)
delete this.$el.__ro__;
this.$el = null;
// this.$el=null;
this._watcher = null;
this._computedWatchers = {};
//ab-aui的內存溢出問題
this.popperElm=null;
if(this.$options){
this.$options.parent=null;
this._parentVnode=null;
this.$options=null;
}
},
