我曾經聽一位喜劇演員說過:
**“我從未在這里,因為我不清楚這里是哪里,是除了那里之外的地方嗎?”**
這句話或多或少地暗喻了在js開發中開發者對于this關鍵字的使用誤區。This指代的是什么?它和日常英語口語中的this是一個意思嗎?
隨著近些年js編程不斷地復雜化,功能多樣化,對于一個程序結構的內部指引、引用也逐漸變多起來
下面讓我們一起來看這一段代碼:
~~~
Game.prototype.restart = function () { this.clearLocalStorage();
this.timer = setTimeout(function(){ this.clearBoard(); }, 0);
};
~~~
運行上面的代碼將會出現如下錯誤:
~~~
Uncaught TypeError: undefined is not a function
~~~
這是為什么?this的調用和它所在的環境密切相關。之所以會出現上面的錯誤,是因為當你在調用 setTimeout()函數的時候, 你實際調用的是window.setTimeout(). 因此,在 setTimeout() 定義的函數其實是在window背景下定義的,而window中并沒有 clearBoard() 這個函數方法。
下面提供兩種解決方案。第一種比較簡單直接的方法便是,把this存儲到一個變量當中,這樣他就可以在不同的環境背景中被繼承下來:
~~~
Game.prototype.restart = function () { this.clearLocalStorage();
var self = this;
this.timer = setTimeout(function(){ self.clearBoard();}, 0); };
~~~
第二種方法便是用bind()的方法,不過這個相比上一種要復雜一些,對于不熟悉bind()的同學可以在微軟官方查看它的使用方法:[https://msdn.microsoft.com/zh-cn/library/ff841995](https://msdn.microsoft.com/zh-cn/library/ff841995)
~~~
Game.prototype.restart = function () { this.clearLocalStorage();
this.timer = setTimeout(this.reset.bind(this), 0); };
Game.prototype.reset = function(){ this.clearBoard();};
~~~
上面的例子中,兩個this均指代的是Game.prototype。