ES6模塊import細節

  寫在前面,目前瀏覽器對ES6的import支持還不是很好,須要用bable轉譯。vue

  ES6引入外部模塊分兩種狀況:瀏覽器

  1.導入外部的變量或函數等;函數

import {firstName, lastName, year} from './profile';

  2.導入外部的模塊,並當即執行spa

import './test'
//執行test.js,但不導入任何變量

  第2種狀況就不用講了,就是執行從頭至尾執行引入的js文件,固然,會忽略js文件裏export。3d

  下面詳細講第1種狀況。code

  兩個js文件,counter.js與my.jsblog

// counter.js
import {a} from './my';
console.log('333333');
console.log(a);
// my.js
console.log('111111');
export var a = 'aaaaaaa';
console.log('222222');

運行的結果是什麼呢?io

 

  貌似沒什麼問題,再看看轉譯後的counter.jsconsole

//#----------------mod start----------------

void function (module, exports){
    window["60ae5ba7"] = {};
    
    "use strict";
    // my.js
    console.log('111111');
    window["60ae5ba7"].a = 'aaaaaaa';
    console.log('222222');
    
}({exports:{}}, {})


//#----------------mod end----------------

//#----------------mod start----------------

void function (module, exports){
    window["3d4fdd69"] = {};
    
    "use strict";
    // counter.js
    var my_1 = window["60ae5ba7"];
    console.log('333333');
    console.log(my_1.a);

  好,暫時不用管那麼多。下面來問題了,我們把console.log(a)這句去掉,看看運行結果編譯

// counter.js
import {a} from './my';
console.log('333333');
// console.log(a);

  咦,只輸出這一句了?咱們明明引入了my模塊了,爲什麼模塊裏的代碼沒有執行呢。

  這要從ES6模塊加載的實質談起。在阮一峯的ES6入門一書裏講到:ES6模塊的運行機制與CommonJS不同,它遇到模塊加載命令import時,不會去執行模塊,而是隻生成一個動態的只讀引用。等到真的須要用到時,再到模塊裏面去取值,換句話說,ES6的輸入有點像Unix系統的「符號鏈接」,原始值變了,import輸入的值也會跟着變。

  但是按照上面說的,那有console.log(a)的時候,應該是輸出3333,1111,2222的順序,而不是1111,2222,333的順序呀。我猜想是上面講的不細緻的緣由,應該分爲編譯時和運行時來講。ES6的這種加載稱爲「編譯時加載」或者靜態加載,即 ES6 能夠在編譯時就完成模塊加載,在編譯的時候,發現了後面有使用到a的地方,就在運行時遇到import的地方直接執行了模塊的代碼。固然只是本身的猜想。 

 

  有一點別忘了:模塊內部的變量不向外暴露的話,外界是沒法使用這些內部變量的。全部有時候會看到,這個模塊引用了一個vue.js,另一個模塊也要引用vue.js,這是由於vue.js內部不少東西沒有暴露,因此都須要引用。

相關文章
相關標籤/搜索