Tree shaking 是一種通過清除多餘代碼方式來優化項目打包體積的技術,專業術語叫 Dead code elimination
簡單來講,就是在保持代碼運作結果不變的前提下,去除無用的代碼
如果把代碼打包比作制作蛋糕,傳統的方式是把雞蛋(帶殼)全部丢進去攪拌,然後放入烤箱,最後把(沒有用的)蛋殼全部挑選并剔除出去
而treeshaking則是一開始就把有用的蛋白蛋黃(import)放入攪拌,最後直接作出蛋糕
也就是說 ,tree shaking 其實是找出使用的代碼
在Vue2中,無論我們使用什麼功能,它們最終都會出現在生産代碼中。主要原因是Vue執行個體在項目中是單例的,捆綁程式無法檢測到該對象的哪些屬性在代碼中被使用到
import Vue from 'vue'
Vue.nextTick(() => {})
而Vue3源碼引入tree shaking特性,将全局 API 進行分塊。如果您不使用其某些功能,它們将不會包含在您的基礎包中
import { nextTick, observable } from 'vue'
nextTick(() => {})
Tree shaking是基于ES6模闆文法(import與exports),主要是借助ES6子產品的靜态編譯思想,在編譯時就能确定子產品的依賴關系,以及輸入和輸出的變量
Tree shaking無非就是做了兩件事:
- 編譯階段利用ES6 Module判斷哪些子產品已經加載
- 判斷那些子產品和變量未被使用或者引用,進而删除對應代碼
下面就來舉個例子:
通過腳手架vue-cli安裝Vue2與Vue3項目
vue create vue-demo
Vue2 項目
元件中使用data屬性
<script>
export default {
data: () => ({
count: 1,
}),
};
</script>
對項目進行打包,體積如下圖
為元件設定其他屬性(compted、watch)
export default {
data: () => ({
question:"",
count: 1,
}),
computed: {
double: function () {
return this.count * 2;
},
},
watch: {
question: function (newQuestion, oldQuestion) {
this.answer = 'xxxx'
}
};
再一次打包,發現打包出來的體積并沒有變化
Vue3 項目
元件中簡單使用
import { reactive, defineComponent } from "vue";
export default defineComponent({
setup() {
const state = reactive({
count: 1,
});
return {
state,
};
},
});
将項目進行打包
在元件中引入computed和watch
import { reactive, defineComponent, computed, watch } from "vue";
export default defineComponent({
setup() {
const state = reactive({
count: 1,
});
const double = computed(() => {
return state.count * 2;
});
watch(
() => state.count,
(count, preCount) => {
console.log(count);
console.log(preCount);
}
);
return {
state,
double,
};
},
});
再次對項目進行打包,可以看到在引入computer和watch之後,項目整體體積變大了