java中this的含义_Javascript中的this的含义
一、幾個問題
JavaScript中的this代表什么?和Java對象里面的this或Objective-C里的self是否有相同的含義?
// demo 1
var a = 2;
function hello() {
console.log(this.a);
}
hello(); // a打印值為?
// demo 2
var a = 2;
function hello() {
console.log(this.a);
}
var obj = {
a: 3,
hello: hello
}
obj.hello(); // a打印值為?
// demo 3
var a = 2;
function hello() {
console.log(this.a);
}
var obj = {
a: 3,
hello: hello
}
var hello2 = obj.hello;
hello2(); // a打印值為?
// demo 4
var a = 2;
function hello() {
console.log(this.a);
}
var obj = {
a: 3,
hello: hello
}
setTimeout(obj.hello, 1000);
二、this的含義
JavaScript中this含義和Java中的this及Objective-C中的self不同,指的不是當前對象。Javascript中this的真正理解應該為當前執行函數的上下文,具體值和函數的調用方式有關。
function hello(context) {
console.log(context.a);
}
var obj1 = {
a: 1
}
var obj2 = {
a: 2
}
hello(obj1); // 1
hello(obj2); // 2
上面的代碼模擬了一下this的用途,hello函數執行時傳入不同的context時,會得到不同的運行結果,因為hello函數運行在不同的的上下文中。相比于上面的context方式,this提供了更加優雅機制來實現上面相同的功能。
function hello() {
console.log(this.a);
}
var obj1 = {
a: 1,
hello: hello
}
var obj2 = {
a: 2,
hello: hello
}
obj1.hello(); // 1
obj2.hello(); // 2
三、this所綁定的對象
在函數運行時,this所綁定的對象和該函數的調用方式有關系,一般來說有四種情況:
3.1、new綁定
JavaScript中,
var obj = {
key: value,
...
};
這種形式的就叫做一個JavaScript對象。除了這種對象的創建方式,也可以通過new關鍵字來創建
function hello(message) {
this.message = message;
}
var obj = new hello("HELLO WORLD!!!");
console.log(obj.message); // HELLO WORLD!!!
通過new關鍵字來調用hello時,hello里面的this就自動綁定到了新創建的對象obj上。
3.2、顯示綁定
JavaScript對象都內置有call和apply函數,可以通過call或者apply來啟動調用一個函數,并明確指定該函數中this所綁定的對象。
function hello() {
console.log(this.a);
}
var obj1 = {
a: 1
}
var obj2 = {
a: 2
}
hello.call(obj1); // 1
hello.call(obj2); // 2
3.3、隱式綁定
如果通過對象屬性的方式來調用一個函數,那么該函數的this就會自動綁定到該對象上
function hello() {
console.log(this.a);
}
var obj1 = {
a: 1,
hello: hello
}
var obj2 = {
a: 2,
hello: hello
}
obj1.hello(); // 1
obj2.hello(); // 2
并且,在對象的屬性引用鏈中,最后最后一層起到作用。下面的例子中,hello函數的this綁定的對象為obj1。
function hello() {
console.log(this.a);
}
var obj1 = {
a: 1,
hello: hello
}
var obj2 = {
a: 2,
obj1: obj1
}
obj2.obj1.hello(); // 1
有一點需要注意,隱私綁定綁定的是在表達式執行時所屬的對象?,F在我們回答demo3的問題,demo3的打印值應該為undefined(嚴格模式)或2(非嚴格模式)。
// demo 3
var a = 2;
function hello() {
console.log(this.a);
}
var obj = {
a: 3,
hello: hello
}
var hello2 = obj.hello;
hello2(); // a打印值為?
demo3的代碼中,var hello2 = obj.hello; 語句將函數地址賦值給了hello2變量,該執行語句并不是函數調用而是一個賦值語句,所以這句可執行語句不能決定this要綁定的對象。真正決定this所綁定對象的是 hell2(); 這句??梢钥吹竭@句可執行語句并不符合隱私綁定的形式,實際上它是一個默認綁定,這是接下來要講的內容。
3.4、默認綁定
什么是默認綁定?如果一個函數的調用不滿足new綁定、顯示綁定、隱私綁定,那么它就是一個默認綁定。如demo1、demo2。默認綁定后,this所綁定的對象有兩種情況:如果JavaScript運行在嚴格模式下,this綁定到了undefined上;如果JavaScript運行在非嚴格模式下,this就綁定到了全局對象上。
3.5、四種綁定的優先級順序
new綁定 > 顯示綁定 > 隱式綁定 > 默認綁定。
下面的例子表明了,如果同時滿足顯示綁定和隱式綁定,則起作用的是顯示綁定。
function hello() {
console.log(this.a);
}
var obj1 = {
a: 1,
hello: hello
}
var obj2 = {
a: 2,
hello: hello
}
obj1.hello.call(obj2); // 2
obj2.hello.call(obj1); // 1
下面的例子表明了,如果同時滿足new綁定和顯示綁定,則起作用的是new綁定。
function hello(message) {
this.message = message;
return {
message: message
}
}
var obj = {
message: ""
};
var hello2 = hello.bind(obj);
hello2("我是顯示綁定!");
var hell3 = new hello2("我是new綁定!");
console.log(obj.message); // 我是顯示綁定!
console.log(hell3.message); // 我是new綁定!
3.6、箭頭函數
ES6中,新引入了箭頭函數。箭頭函數不滿足以上四種規則,它的this對象來自外層作用域中this多綁定的對象。
function hello() {
return (a) => {
console.log(this.a);
}
}
var obj1 = {
a: 1
}
var obj2 = {
a: 2
}
var hello2 = hello.call(obj1);
hello2.call(obj2); // 1
可以看到,hello中返回的箭頭函數實際上是一個閉包,該閉包捕獲了hello的this對象,且無法通過顯示綁定修改。
hello2.call(obj2);語句雖然想要將箭頭函數顯示綁定到obj2對象中,但失敗了。
四、一些解釋
// demo 4
var a = 2;
function hello() {
console.log(this.a);
}
var obj = {
a: 3,
hello: hello
}
setTimeout(obj.hello, 1000);
demo4最后應用的是默認綁定,那么問題來了,如果我想要通過setTimeout函數調用hello,并且調用時綁定到obj對象上,那么我應該如何實現呢?見下面的代碼所示:
function bind(fn, obj) {
return function(arg) {
return fn.call(obj, arg);
};
}
var a = 2;
function hello() {
console.log(this.a);
}
var obj = {
a: 3,
hello: hello
}
var hello2 = bind(hello, obj);
setTimeout(hello2, 1000);
可以通過bind來實現,bind是使用顯示綁定,通過構造一個包裹函數,該包裹函數將hello強制綁定到obj對象上,從而實現我們的目的。bind函數的用途非常常見,以至于JavaScript已經內置了該函數,在3.5中的代碼示例中我們已經展示過相關使用。
參看《你不知道的JavaScript(上卷)》
總結
以上是生活随笔為你收集整理的java中this的含义_Javascript中的this的含义的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 南华大学java补考_关于2017年秋季
- 下一篇: java获取ua浏览器指纹_头条:如何获