Node Global對象

標籤: node Globaljavascript


全部屬性均可以在程序的任何地方訪問,即全局變量。在javascript中,一般window是全局對象,而node.js的全局對象是global,全部全局變量都是global對象的屬性,如:consoleprocess等。java

全局對象與全局變量

global最根本的做用是做爲全局變量的宿主。知足如下條件成爲全局變量。node

  • 在最外層定義的變量
  • 全局對象的屬性
  • 隱式定義的變量(未定義直接賦值的變量)

node.js中不可能在最外層定義變量,由於全部的用戶代碼都是屬於當前模塊的,而模塊自己不是最外層上下文。node.js中也不提倡自定義全局變量。數組

Node提供如下幾個全局對象,它們是全部模塊均可以調用的。

  • global:表示Node所在的全局環境,相似於瀏覽器的window對象。須要注意的是,若是在瀏覽器中聲明一個全局變量,其實是聲明瞭一個全局對象的屬性,好比var x = 1等同於設置window.x = 1,可是Node不是這樣,至少在模塊中不是這樣(REPL環境的行爲與瀏覽器一致)。在模塊文件中,聲明var x = 1,該變量不是global對象的屬性,global.x等於undefined。這是由於模塊的全局變量都是該模塊私有的,其餘模塊沒法取到。瀏覽器

  • process:該對象表示Node所處的當前進程,容許開發者與該進程互動。bash

  • console:指向Node內置的console模塊,提供命令行環境中的標準輸入、標準輸出功能。函數

process

  • argv 執行參數
  • env 環境變量
  • pid 當前進程id
  • chdir/cwd chdir能夠改變執行的工做目錄 cwd表明的時當前目錄
  • nextTick 下一隊列
  • stdout
  • stderr
  • stdin
  • kill
  • exit
// 標準輸出 1
process.stdout.write('hello');
複製代碼
// 錯誤輸出 2
process.stderr.write('world');
複製代碼
// 0 標準輸入 
process.stdin.on('data',function (data) {
  console.log(data.toString())
});
複製代碼
// node中有一個專門作斷言的庫 assert 測試用
console.assert(1===1===1,'錯誤');
複製代碼
// 測試兩個代碼之間的執行時間 
console.time('tag1'); 
console.timeEnd('tag1');
複製代碼
// 解析打印的詳細信息
// 內部調用的是util.inspect()庫的方法;
console.dir(); 
複製代碼
// yargs庫 能夠解析用戶執行命令時傳遞的參數
console.log(process.argv);
let args = {}
process.argv.slice(2).forEach((arg,index) => {
  if(arg.includes('--')){
    args[arg.slice(2)] = process.argv.slice(2)[index+1];
  }
});
console.log(args);
複製代碼
// 環境變量 set my=dev&&node xxx.js (關掉創就就消失了);
// 用來區分代碼中的環境
let url = '';
if(process.env.my === 'dev'){
  url = 'http://localhost:3000'
}else{
  url = 'http://fullstackjavascript'
}
console.log(url);

複製代碼

Node還提供一些全局函數。

  • setTimeout():用於在指定毫秒以後,運行回調函數。實際的調用間隔,還取決於系統因素。間隔的毫秒數在1毫秒到2,147,483,647毫秒(約24.8天)之間。若是超過這個範圍,會被自動改成1毫秒。該方法返回一個整數,表明這個新建定時器的編號。
  • clearTimeout():用於終止一個setTimeout方法新建的定時器。
  • setInterval():用於每隔必定毫秒調用回調函數。因爲系統因素,可能沒法保證每次調用之間正好間隔指定的毫秒數,但只會多於這個間隔,而不會少於它。指定的毫秒數必須是1到2,147,483,647(大約24.8天)之間的整數,若是超過這個範圍,會被自動改成1毫秒。該方法返回一個整數,表明這個新建定時器的編號。
  • clearInterval():終止一個用setInterval方法新建的定時器。
  • require():用於加載模塊。
  • Buffer():用於操做二進制數據。

Node提供兩個全局變量,都以兩個下劃線開頭。

  • _filename:指向當前運行的腳本文件名。
  • _dirname:指向當前運行的腳本所在的目錄。 除此以外,還有一些對象其實是模塊內部的局部變量,指向的對象根據模塊不一樣而不一樣,可是全部模塊都適用,能夠看做是僞全局變量,主要爲module, module.exports, exports等。

module.exports vs exports

若是想不借助global,在不一樣模塊之間共享代碼,就須要用到exports屬性。使人有些迷惑的是,在node.js裏,還有另一個屬性,是module.exports。通常狀況下,這2個屬性的做用是一致的,可是若是對exports或者module.exports賦值的話,又會呈現出使人奇怪的結果。測試

首先,exports和module.exports都是某個對象的引用(reference),初始狀況下,它們指向同一個object,若是不修改module.exports的引用的話,這個object稍後會被導出。ui

exports  module.exports
    |         /
    |        /
    V       V
     Object
複製代碼

因此若是隻是給對象添加屬性,不改變exports和module.exports的引用目標的話,是徹底沒有問題的。this

可是有時候,但願導出的是一個構造函數,那麼通常會這麼寫:

/ b.js
module.exports = function (name, age) {
    this.name = name;
    this.age = age;
}

exports.sex = "male";
複製代碼
var Person = require("./b");
var person = new Person("Tony", 33);
console.log(person); // {name:"Tony", age:33}
console.log(Person.sex); // undefined
複製代碼

這個sex屬性不會導出,由於引用關係已經改變:

exports  module.exports
    |          |
    |          |
    V          V
   function   Object
複製代碼

若是但願把sex屬性也導出,就須要這樣寫:

exports = module.exports = function (name, age) {
    this.name = name;
    this.age = age;
}

exports.sex = "male";
複製代碼

再好比,不少時候能夠看到,在node中有兩種方法能夠輸出變量:

// 方法一:對module.exports賦值:

function hello(){

console.log('hello word');

}

function greet(name){

console.log('hello'+name);

}

module.exports = {

hello:hello,

greet:greet

}

// 方法二直接使用exports:

function hello(){

console.log('hello word');

}

function greet(name){

console.log('hello'+name);

}

function hello(){

console.log('hello word');

}
exports.hello = hello;
exports.greet = greet;

//可是不能夠直接對exports賦值,直接賦值的話代碼能夠執行,可是沒有輸出任何變量(exports = {hello = hello,greet = greet})。

複製代碼

load()函數最終返回module.exports;

var load = function(exports,module){

    return module.exports;

}

var exported = load(module.exports,module);
複製代碼

也就是說,默認狀況下node準備的exports和module.exports實際上指向同一個空對象,可是若是咱們輸出的是函數或者數組,就只能給module.exports賦值。

總結

  • node.js 設計的2個導出引用的對象,反而增長了迷惑性。
  • 避免污染全局空間。
相關文章
相關標籤/搜索