對於我們初學者來說,在使用js建立對象時,不適應閉包的寫法,經常容易忘記使用new關鍵字而犯錯誤。
閉包是有權訪問另外一個函數範圍中變數的函數,即在一個函數內部建立另外一個函數。我們將這個閉包作為建立對象的建構函式,這樣他既是閉包又是可執行個體化對象的函數,即可訪問到類函數範圍中變數,如bookNum這個變數,此時這個變數叫做靜態私人變數,並且checkBook()可稱之為靜態私人方法。當然閉包內部也有自身的私人變數以及私人方法如price,checkID()。
//利用閉包實現var Book=(function(){//靜態私人變數var bookNum = 0;//建立私人方法function checkBook(name){}//建立類function book(newId,newName,newPrice){ //私人變數 var name,price; //私人方法 function checkID(id){} //特權方法 this.getName=function(){}; this.getPrice=function(){}; this.setName=function(){}; this.setPrice=function(){}; //公有屬性 this.id=newId; //公有方法 this.copy=function(){}; bookNum++ if(bookNum>100){ throw new Error('沒有更多書.'); } this.setName(name); this.setPrice(price);} //構建原型 _book.prototype={ //靜態公有屬性 isJSBook:false, //靜態共有方法 display:function(){} }; //返回類 return _book;})();
new建立類
//圖書類var Book = function(title,time,type){ this.title = title; this.time = time; this.type = type;}//執行個體化一本書var book = Book('javascript','2014','js');結果:console.log(book); //undefinedconsole.log(window.title); //javascriptconsole.log(window.time); //2014console.log(window.type); //js
new關鍵字作用可以看作是對當前對象的this不停地賦值,然而例子中沒有用new,所以就會直接執行這個函數,而這個函數在全域範圍中執行了,所以在全域範圍中this指向的是當前對象自然就是全域變數,在頁面中全域變數為window
所以,可以使用如下安全模式:
//圖書安全類var Book = function(title,time,type){//判斷執行過程中this是否是當前這個對象(如果是說明是用new建立的) if(this instanceof Book){ this.title = title; this.time = time; this.type = type; //否則重新建立這個對象 }else{ return new Book(title,time,type); }}var book= Book('javascript','2014','js');//輸出結果:console.log(book); //Bookconsole.log(book.title); //javascriptconsole.log(book.time); //2014console.log(book.type); //jsconsole.log(window.title); //undefinedconsole.log(window.time); //undefinedconsole.log(window.type); //undefined