JavaScript中函數的this物件是函數在執行時所處的作用域(例:當在網頁的全域作用域中呼叫函數時,this物件引用的就是window)。
JavaScript的this和Java等物件導向語言中的this大不一樣,bind()、call()和apply()函數更是將this的靈活度進一步延伸。
為了保證可讀性,本文採用意譯而非直譯。另外,本文版權歸原作者所有,翻譯僅用於學習。
如果對JavaScript的關鍵字this理解不夠深刻,有時候會掉入意想不到的坑。這裡我們總結了5條通用規則來幫助你判斷this到底指向什麼。雖然沒有囊括所有的情況,但日常大部分情況都可以使用這些規則來正確推論。
this的值通常是由所在函數的執行環境決定,也就是說要看函數是如何被調用的;
同一個函數每一次調用,this都可能指向不同的物件;
全域物件(Global Object)
開啟Chrome瀏覽器開發者面板(Windows: Ctrl Shift J)(Mac: Cmd Option J),並且輸入:
console.log(this);
看看輸出了什麼?
// Window {}
window物件!因為在全域作用域下,this指向全域物件。在瀏覽器中全域物件就是window物件。
為了讓你更清楚地理解為什麼this會指向window對象,我們來看另外一個例子:
var myName = 'Brandon';
我們可以透過在控制台輸入myName來存取其值:
myName // 输出 'Brandon'
其實,所有在全域定義的變數都會綁定到window物件。讓我們來做以下測試:
window.myName // 输出 'Brandon' window.myName === myName // 输出 true
現在我們將this放到函數內部,看看有何效果。
function test(){ return this; } test();
你會發現this依然指向全域的window物件。因為this關鍵字沒有處於一個聲明的物件內部,預設指向全域window物件。這一點可能對於大部分初學者來說有點難以理解。當你讀完這篇文章,你就會豁然開朗。
注意:如果在strcit模式下,上面的例子this為undefined。
聲明的物件(Declared Object)
當this關鍵字在一個宣告物件內部使用,其值會被綁定到呼叫該this的函數的最近的父對象。我們用例子來說明這個問題:
var person = { first: 'John', last: 'Smith', full: function() { console.log(this.first + ' ' + this.last); } }; person.full(); // 输出 'John Smith'
在被宣告的物件person中的full函數裡面使用了this, 那麼呼叫this的full函數的最近的父物件就是person, 因此,this指向person。
為了更好的描述this實際上是指向person物件的,你可以拷貝如下程式碼到瀏覽器控制台,將this列印出來。
var person = { first: 'John', last: 'Smith', full: function() { console.log(this); } }; person.full(); // 输出 Object {first: "John", last: "Smith", full: function}
我們接下來看一個更複雜的例子:
var person = { first: 'John', last: 'Smith', full: function() { console.log(this.first + ' ' + this.last); }, personTwo: { first: 'Allison', last: 'Jones', full: function() { console.log(this.first + ' ' + this.last); } } };
在這裡我們有嵌套的對象,在這個時候,this分別指向誰呢?我們將其印出來看看:
person.full(); // 输出 'John Smith' person.personTwo.full(); // 输出 'Allison Jones'
你會發現滿足我們前面所描述的規則:其值會被綁定到呼叫this的函數的最近的父物件。
new關鍵字
當使用new關鍵字建立一個新的對象,this會綁定到這個新對象。我們來看一個例子:
function Car(make, model) { this.make = make; this.model = model; };
根據第一條規則,你可能會推斷this指向全域物件。但是如果我們使用new關鍵字來宣告一個新的變量,Car函數中的this將會綁定一個新的空對象,然後初始化this.make和this.model的值。
var myCar = new Car('Ford', 'Escape'); console.log(myCar); // 输出 Car {make: "Ford", model: "Escape"}
call, bind, 和apply
我們可以顯示的在call(),bind(),apply()中設定this的綁定物件。這三個函數很類似,但是我們需要注意它們微小的差異。
我們來看一個例子:
function add(c, d) { console.log(this.a + this.b + c + d); } add(3,4); // 输出 NaN
add函數輸出NaN, 因為this.a和this.b未定義。
現在我們引入對象,並且使用call()和apply()來呼叫:
function add(c, d) { console.log(this.a + this.b + c + d); } var ten = {a: 1, b: 2}; add.call(ten, 3, 4); // 输出 10 add.apply(ten, [3,4]); // 输出 10
當我們使用add.call(),第一個參數是this需要綁定的對象,剩下的是add函數本來的參數。
因此,this.a指向ten.a,this.b指向ten.b。 add.apply()也類似,除了第二個參數是一個數組,用來儲存add函數的參數。
bind()函數和call()類似,但是bind()函數不會立即被呼叫。 bind()函數會傳回一個函數,並且將this綁定好。接下來我們來用例子來幫助理解bind()函數的應用場景:
var small = { a: 1, go: function(b,c,d){ console.log(this.a+b+c+d); } } var large = { a: 100 }
執行:
small.go(2, 3, 4); // 输出 10
如果我們想要使用large.a的值,而不是small.a呢?我們可以使用call/apply:
small.go.call(large, 2, 3, 4); // 输出 109
但是,如果我們現在還不知道這三個參數應該傳入什麼值,我們該怎麼辦呢?我們可以使用bind:
var bindTest = small.go.bind(large, 2);
如果我們將bindTest在控制台下列印出來,我們會看到:
console.log(bindTest); // 输出 function (b,c,d){console.log(this.a+b+c+d);}
注意:該函數已經將this綁定到large對象,並且傳入了第一個參數b。所以,我們接下來是需要傳入餘下的參數即可:
bindTest(3, 4); // 输出 109
上面是我整理給大家的,希望今後會對大家有幫助。
相關文章:
JS中this的指向以及call、apply的作用(圖文教程)
JS中this的指向以及call、apply的作用_基礎知識
PHP 中self、static、$this 的區別和後期靜態綁定詳解
以上是JavaScript中this詳細解答(圖文教學)的詳細內容。更多資訊請關注PHP中文網其他相關文章!

Python更適合初學者,學習曲線平緩,語法簡潔;JavaScript適合前端開發,學習曲線較陡,語法靈活。 1.Python語法直觀,適用於數據科學和後端開發。 2.JavaScript靈活,廣泛用於前端和服務器端編程。

Python和JavaScript在社區、庫和資源方面的對比各有優劣。 1)Python社區友好,適合初學者,但前端開發資源不如JavaScript豐富。 2)Python在數據科學和機器學習庫方面強大,JavaScript則在前端開發庫和框架上更勝一籌。 3)兩者的學習資源都豐富,但Python適合從官方文檔開始,JavaScript則以MDNWebDocs為佳。選擇應基於項目需求和個人興趣。

從C/C 轉向JavaScript需要適應動態類型、垃圾回收和異步編程等特點。 1)C/C 是靜態類型語言,需手動管理內存,而JavaScript是動態類型,垃圾回收自動處理。 2)C/C 需編譯成機器碼,JavaScript則為解釋型語言。 3)JavaScript引入閉包、原型鍊和Promise等概念,增強了靈活性和異步編程能力。

不同JavaScript引擎在解析和執行JavaScript代碼時,效果會有所不同,因為每個引擎的實現原理和優化策略各有差異。 1.詞法分析:將源碼轉換為詞法單元。 2.語法分析:生成抽象語法樹。 3.優化和編譯:通過JIT編譯器生成機器碼。 4.執行:運行機器碼。 V8引擎通過即時編譯和隱藏類優化,SpiderMonkey使用類型推斷系統,導致在相同代碼上的性能表現不同。

JavaScript在現實世界中的應用包括服務器端編程、移動應用開發和物聯網控制:1.通過Node.js實現服務器端編程,適用於高並發請求處理。 2.通過ReactNative進行移動應用開發,支持跨平台部署。 3.通過Johnny-Five庫用於物聯網設備控制,適用於硬件交互。

我使用您的日常技術工具構建了功能性的多租戶SaaS應用程序(一個Edtech應用程序),您可以做同樣的事情。 首先,什麼是多租戶SaaS應用程序? 多租戶SaaS應用程序可讓您從唱歌中為多個客戶提供服務

本文展示了與許可證確保的後端的前端集成,並使用Next.js構建功能性Edtech SaaS應用程序。 前端獲取用戶權限以控制UI的可見性並確保API要求遵守角色庫

JavaScript是現代Web開發的核心語言,因其多樣性和靈活性而廣泛應用。 1)前端開發:通過DOM操作和現代框架(如React、Vue.js、Angular)構建動態網頁和單頁面應用。 2)服務器端開發:Node.js利用非阻塞I/O模型處理高並發和實時應用。 3)移動和桌面應用開發:通過ReactNative和Electron實現跨平台開發,提高開發效率。


熱AI工具

Undresser.AI Undress
人工智慧驅動的應用程序,用於創建逼真的裸體照片

AI Clothes Remover
用於從照片中去除衣服的線上人工智慧工具。

Undress AI Tool
免費脫衣圖片

Clothoff.io
AI脫衣器

AI Hentai Generator
免費產生 AI 無盡。

熱門文章

熱工具

mPDF
mPDF是一個PHP庫,可以從UTF-8編碼的HTML產生PDF檔案。原作者Ian Back編寫mPDF以從他的網站上「即時」輸出PDF文件,並處理不同的語言。與原始腳本如HTML2FPDF相比,它的速度較慢,並且在使用Unicode字體時產生的檔案較大,但支援CSS樣式等,並進行了大量增強。支援幾乎所有語言,包括RTL(阿拉伯語和希伯來語)和CJK(中日韓)。支援嵌套的區塊級元素(如P、DIV),

SAP NetWeaver Server Adapter for Eclipse
將Eclipse與SAP NetWeaver應用伺服器整合。

WebStorm Mac版
好用的JavaScript開發工具

MinGW - Minimalist GNU for Windows
這個專案正在遷移到osdn.net/projects/mingw的過程中,你可以繼續在那裡關注我們。 MinGW:GNU編譯器集合(GCC)的本機Windows移植版本,可自由分發的導入函式庫和用於建置本機Windows應用程式的頭檔;包括對MSVC執行時間的擴展,以支援C99功能。 MinGW的所有軟體都可以在64位元Windows平台上運作。

VSCode Windows 64位元 下載
微軟推出的免費、功能強大的一款IDE編輯器