目錄
成都創(chuàng)新互聯(lián)網(wǎng)站建設(shè)公司一直秉承“誠(chéng)信做人,踏實(shí)做事”的原則,不欺瞞客戶,是我們最起碼的底線! 以服務(wù)為基礎(chǔ),以質(zhì)量求生存,以技術(shù)求發(fā)展,成交一個(gè)客戶多一個(gè)朋友!專注中小微企業(yè)官網(wǎng)定制,成都做網(wǎng)站、網(wǎng)站設(shè)計(jì),塑造企業(yè)網(wǎng)絡(luò)形象打造互聯(lián)網(wǎng)企業(yè)效應(yīng)。Node.js是什么
基礎(chǔ)使用
Node的REPL
全局變量
模塊化設(shè)計(jì)
CommondJS規(guī)范
基礎(chǔ)使用exports和module.exports
require
CommondJS優(yōu)缺點(diǎn)
AMD和CMD規(guī)范
ES_Module
基本使用方法
導(dǎo)出
導(dǎo)入
結(jié)合使用
默認(rèn)導(dǎo)出
ES Module解析流程
Node與瀏覽器的對(duì)比
在瀏覽器中,HTML與CSS交給Blink處理,如果其發(fā)現(xiàn)了JS代碼,就會(huì)交給V8處理
而Node是直接V8處理JS代碼,Node主要由JS(api)、C++和C語(yǔ)言編寫,libuv主要綁定js與操作系統(tǒng)的操作
下載地址
Node.js
基礎(chǔ)使用可以在VScode中的終端使用node
console.log(1123123);
console.log('asdada');
在終端中直接? node XXX.js(XXX是文件名,在運(yùn)行時(shí)終端的文件域必須和該文件一致)
如果要從終端輸入?yún)?shù)
console.log(1123123);
console.log('asdada');
console.log(process.argv);
結(jié)果:
1123123
asdada
[
'C:\\Program Files\\nodejs\\node.exe',
'C:\\Users\\12860\\Desktop\\品優(yōu)購(gòu)項(xiàng)目\\test.js',
'num1=123'
]
也就是說(shuō)??process.argv輸出的是一個(gè)數(shù)組,你輸入的數(shù)據(jù)在數(shù)組的第3個(gè)之后??
Node的REPL在控制臺(tái)輸入node,可以一行一行輸入并執(zhí)行js代碼
用的很少
全局變量例如global,類似于window
console.log(global);
可以看到j(luò)s中的全局變量
Object [global] {
global: [Circular *1],
queueMicrotask: [Function: queueMicrotask],
clearImmediate: [Function: clearImmediate],
setImmediate: [Function: setImmediate] {
[Symbol(nodejs.util.promisify.custom)]: [Getter]
},
structuredClone: [Function: structuredClone],
clearInterval: [Function: clearInterval],
clearTimeout: [Function: clearTimeout],
setInterval: [Function: setInterval],
setTimeout: [Function: setTimeout] {
[Symbol(nodejs.util.promisify.custom)]: [Getter]
},
atob: [Function: atob],
btoa: [Function: btoa],
performance: Performance {
nodeTiming: PerformanceNodeTiming {
name: 'node',
entryType: 'node',
startTime: 0,
duration: 33.55670002102852,
nodeStart: 2.157499998807907,
v8Start: 4.655900001525879,
bootstrapComplete: 23.560699999332428,
environment: 13.318800002336502,
loopStart: -1,
loopExit: -1,
idleTime: 0
},
timeOrigin: 1668353099915.782
},
fetch: [AsyncFunction: fetch]
}
對(duì)于瀏覽器來(lái)說(shuō)有window,對(duì)于node來(lái)說(shuō)有g(shù)lobal,所以創(chuàng)造了一個(gè)總的全局變量,在兩個(gè)地方都能用,叫g(shù)lobalthis?
模塊化設(shè)計(jì)解釋一下第二點(diǎn)
對(duì)于之前的做法,如果我有很多js文件,第一個(gè)文件aaa.js定義了var name = 111
第二個(gè)文件bbb.js定義var name = 222
當(dāng)我在第三個(gè)js文件通過(guò)scrip src方式引入這兩個(gè)js文件時(shí),這個(gè)name變量就會(huì)變得模糊
而模塊化設(shè)計(jì)的要求是,不同模塊的變量是不會(huì)互相影響的,且外部無(wú)法訪問(wèn)
但是肯定不希望所有的變量,外部都不能訪問(wèn),所有可以通過(guò)一些方法導(dǎo)出自己希望外部能訪問(wèn)的內(nèi)容,既第三點(diǎn)
立即執(zhí)行函數(shù)可以解決變量沖突的問(wèn)題,如果在aaa.js和bbb.js中的代碼都放入立即執(zhí)行函數(shù)中,由于函數(shù)本身就有作用域,所以不會(huì)互相影響
但是如果外部想調(diào)用變量,就必須確定立即執(zhí)行函數(shù)的返回對(duì)象,這會(huì)增加使用難度
CommondJS規(guī)范基礎(chǔ)使用exports和module.exports在test.js里面寫
const name = 'lmx'
const age= 18
const fn = function(){
console.log(123);
}
exports.name = name
exports.age = age
exports.fn = fn
在mian.js寫
const test = require('./test.js')
console.log(test);
console.log(test.name);
test.fn()
必須要用node運(yùn)行main.js
其實(shí)本質(zhì)就是引用賦值
test.js創(chuàng)建了exports對(duì)象,然后往里面寫入元素name age fn,但是exports變量保留的是該對(duì)象的地址
而require也是獲取的對(duì)象的地址,所以兩者指向的是同一個(gè)對(duì)象
那么在test.js里面改變值,也會(huì)影響到main.js
例如,test.js:
const name = 'lmx'
const age= 18
const fn = function(){
console.log(123);
}
exports.name = name
exports.age = age
exports.fn = fn
setTimeout(()=>{
exports.name = 'qweqwe'
},2000)
main.js
const test = require('./test.js')
console.log(test);
console.log(test.name);
test.fn()
setTimeout(()=>{
console.log(test.name);
},2500)
{ name: 'lmx', age: 18, fn: [Function: fn] }
lmx
123
qweqwe
但是上述方法在開發(fā)中使用的很少,一般用module.exports
將test.js中的exprots改為:
const name = 'qwe'
const age = 17
module.exports.name = name
module.exports.age = age
main.js不需要改
看上去還變復(fù)雜了,從本質(zhì)上來(lái)說(shuō),這種方法會(huì)創(chuàng)造一個(gè)module對(duì)象,該對(duì)象里面包含了一個(gè)exports,指向之前創(chuàng)造的對(duì)象
所以說(shuō)這里左邊的exports和module.exports其實(shí)是一個(gè)東西,因?yàn)橹赶虻氖峭粋€(gè)對(duì)象
在require的時(shí)候,其實(shí)node本質(zhì)上拿到的是module.exports,但是因?yàn)閙odule.exports===exports,所有現(xiàn)在看來(lái)兩種方式是一樣的
真實(shí)開發(fā)做法是
const name = 'qwe'
const age = 17
console.log(age);
module.exports={
name,
age
}
exports.name = 'hhhhh'
本質(zhì)是,這里會(huì)創(chuàng)造一個(gè)新的對(duì)象,module.exports指向這個(gè)對(duì)象,那么這個(gè)對(duì)象跟之前的exports對(duì)象就沒有關(guān)系了
使用require獲取的也是這個(gè)新的對(duì)象,所有改exports.name沒有意義了
結(jié)果是{ name: 'qwe', age: 17 }
require例如,內(nèi)置模塊包含了很多方法
const test = require('path')
console.log(test);
{
resolve: [Function: resolve],
normalize: [Function: normalize],
isAbsolute: [Function: isAbsolute],
join: [Function: join],
relative: [Function: relative],
toNamespacedPath: [Function: toNamespacedPath],
dirname: [Function: dirname],
basename: [Function: basename],
extname: [Function: extname],
format: [Function: bound _format],
parse: [Function: parse],
sep: '\\',
delimiter: ';',
win32: [Circular *1],
posix:{
resolve: [Function: resolve],
normalize: [Function: normalize],
isAbsolute: [Function: isAbsolute],
join: [Function: join],
relative: [Function: relative],
toNamespacedPath: [Function: toNamespacedPath],
dirname: [Function: dirname],
basename: [Function: basename],
extname: [Function: extname],
format: [Function: bound _format],
parse: [Function: parse],
sep: '/',
delimiter: ':',
win32: [Circular *1],
posix: [Circular *2],
_makeLong: [Function: toNamespacedPath]
},
_makeLong: [Function: toNamespacedPath]
}
意思是有的時(shí)候可以省略.js等
第三種情況,X即不是內(nèi)置模塊,也不是文件,例如
const test = require('why')
它會(huì)找上層文件夾中下的node_modules文件夾,這個(gè)文件夾名字是固定的,然后再在node_modules文件夾里面找why文件夾,再找why文件夾下的index.js
如果沒找到node_modules,就返回再上一層文件夾接著找,直到找到或者找到根目錄為止
所以在npm install axios的時(shí)候,其實(shí)就是創(chuàng)建了一個(gè)node_modules文件夾,把a(bǔ)xios相關(guān)的文件放進(jìn)去了
CommondJS優(yōu)缺點(diǎn)AMD和CMD規(guī)范已經(jīng)用的很少了,做一個(gè)了解吧
ES_ModuleES module是ES6新增的JS模塊化的功能,如果瀏覽器支持ES6則可以直接使用
如果不支持,一般是通過(guò)webpack打包之后再接入瀏覽器
基本使用方法在html引入js這么寫,加type = 'module',這樣就可以創(chuàng)建獨(dú)立的作用域,不會(huì)互相影響
但是在打開時(shí),必須打開服務(wù),例如使用live server
導(dǎo)出const name = 'why'
const age =14
export{
name,
age
}
這個(gè)地方,export{}不是新建的一個(gè)對(duì)象,只是大括號(hào)將標(biāo)識(shí)符包含起來(lái)
也可以在定義的時(shí)候直接導(dǎo)出
const name = 'why'
export const age =14
導(dǎo)入import {name,age }from './test.js'
console.log(name );
console.log(age);
導(dǎo)入的時(shí)候可以起個(gè)別名
import {name as fname,age }from './test.js'
console.log(fname );
console.log(age);
導(dǎo)入語(yǔ)句只能寫在頂端,不能寫在邏輯代碼里面?
例如
let flag = true
if(flag){
import{name,age} from './test.js'
}
這種會(huì)直接報(bào)錯(cuò)
但是我就是想放在邏輯里面使用呢,比如當(dāng)某種條件成立的時(shí)候才導(dǎo)入
可以用到import函數(shù)
let flag = true
if(flag){
let promise1 = import('./test.js')
promise1.then(res=>{
console.log(res.name);
console.log(res.age);
res.fn()
})
}
因?yàn)樵摵瘮?shù)是異步的,其返回值是一個(gè)promise,調(diào)用then拿到結(jié)果?
結(jié)合使用如果現(xiàn)在有很多js文件,基本上每個(gè)文件都導(dǎo)出了一些方法
如果index,html想得到這些方法,就得一個(gè)一個(gè)script src=
一般的做法是,再新建一個(gè)index.js,里面將那些js文件導(dǎo)入,再直接導(dǎo)出,所以在html文件中就可以直接只導(dǎo)入index.js
那么在index.js里面就可以這么寫
export{getdata,getname} from './aaa.js'
export{getdata1,getname2} from './bbb.js'
默認(rèn)導(dǎo)出如果一個(gè)js文件,他的文件名就已經(jīng)代表了他的功能,且只需要導(dǎo)出一個(gè)東西,就可以使用默認(rèn)導(dǎo)出
const name = 'why'
export default name
如果導(dǎo)出的函數(shù),甚至可以不寫函數(shù)名字
export default function(){
console.log('asdasd');
}
很顯然,一個(gè)模塊只能有一個(gè)默認(rèn)導(dǎo)出
之前的導(dǎo)入中 ,都需要導(dǎo)出和導(dǎo)入的變量名字保持一直(除非使用as改名),使用默認(rèn)導(dǎo)出,就可以在導(dǎo)入的時(shí)候自己設(shè)置一個(gè)名字
import aaa from './test.js'
console.log(aaa);
ES Module解析流程首先第一步,對(duì)于js文件進(jìn)行下載,解析為 模塊記錄module record,例如如果在index.html中引入了main.js,那么會(huì)首先下載這個(gè)js文件。
如果js文件中也存在導(dǎo)入語(yǔ)句,那么跟第一步一樣,先下載對(duì)應(yīng)的js文件,創(chuàng)建模塊記錄,這里是會(huì)直接搜索文件的最開始部分有沒有import語(yǔ)句,所以不能將其放入邏輯判斷中。
這里還會(huì)生成一個(gè)映射表 module map,放入js文件的地址和對(duì)應(yīng)的??module record,在這個(gè)圖中main.js引入的counter.js,如果別的文件也引入了counter.js,那么就可以在這個(gè)表中直接拿到 module record
第二步,如果有導(dǎo)出語(yǔ)句,例如export const age = 18,那么會(huì)生成一個(gè)模塊環(huán)境記錄? module environment record 放置 age變量,但是它是沒有值的。
值得注意的是,上述兩步是沒有執(zhí)行一行代碼的
第三步,運(yùn)行,填充環(huán)境記錄中的變量值,例如填充age 的值是多少,在后續(xù)別的模塊import這個(gè)age的時(shí)候,就可以從這里拿到
你是否還在尋找穩(wěn)定的海外服務(wù)器提供商?創(chuàng)新互聯(lián)www.cdcxhl.cn海外機(jī)房具備T級(jí)流量清洗系統(tǒng)配攻擊溯源,準(zhǔn)確流量調(diào)度確保服務(wù)器高可用性,企業(yè)級(jí)服務(wù)器適合批量采購(gòu),新人活動(dòng)首月15元起,快前往官網(wǎng)查看詳情吧