標籤:建立 內容 return prototype orange 參數 地方 class 變數
普通函數調用
function person(){ this.name="xl"; console.log(this); console.log(this.name);}person(); //輸出 window xl
在這段代碼中person函數作為普通函數調用,實際上person是作為全域對象window的一個方法來進行調用的,即window.person();所以這個地方是window對象調用了person方法,那麼person函數當中的this即指window,同時window還擁有了另外一個屬性name,值為xl.
var name="xl";function person(){ console.log(this.name);}person(); //輸出 xl
同樣這個地方person作為window的方法來調用,在代碼的一開始定義了一個全域變數name,值為xl,它相當於window的一個屬性,即window.name="xl",又因為在調用person的時候this是指向window的,因此這裡會輸出xl.
作為方法調用
var name="XL";var person={ name:"xl", showName:function(){ console.log(this.name); }}person.showName(); //輸出 xl //這裡是person對象調用showName方法,很顯然this關鍵字是指向person對象的,所以會輸出name var showNameA=person.showName;showNameA(); //輸出 XL//這裡將person.showName方法賦給showNameA變數,此時showNameA變數相當於window對象的一個屬性,因此showNameA()執行的時候相當於window.showNameA(),即window對象調用showNameA這個方法,所以this關鍵字指向window
另例
var personA={ name:"xl", showName:function(){ console.log(this.name); }}var personB={ name:"XL", sayName:personA.showName} personB.sayName(); //輸出 XL//雖然showName方法是在personA這個對象中定義,但是調用的時候卻是在personB這個對象中調用,因此this對象指向作為建構函式調用
function Person(name){ this.name=name;}var personA=Person("xl");console.log(personA.name); // 輸出 undefinedconsole.log(window.name);//輸出 xl//上面代碼沒有進行new操作,相當於window對象調用Person("xl")方法,那麼this指向window對象,並進行賦值操作window.name="xl". var personB=new Person("xl");console.log(personB.name);// 輸出 xl//這部分代碼的解釋見下
new操作符
//下面這段代碼類比了new操作符(執行個體化對象)的內部過程function person(name){ var o={}; o.__proto__=Person.prototype; //原型繼承 Person.call(o,name); return o;}var personB=person("xl"); console.log(personB.name); // 輸出 xl
在person裡面首先建立一個Null 物件o,將o的proto指向Person.prototype完成對原型的屬性和方法的繼承
Person.call(o,name)這裡即函數Person作為apply/call調用(具體內容下方),將Person對象裡的this改為o,即完成了o.name=name操作
返回對象o。
因此`person("xl")`返回了一個繼承了`Person.prototype`對象上的屬性和方法,以及擁有`name`屬性為"xl"的對象,並將它賦給變數`personB`.所以`console.log(personB.name)`會輸出"xl"
call/apply方法的調用
在JS裡函數也是對象,因此函數也有方法。從Function.prototype上繼承到Function.prototype.call/Function.prototype.apply方法
call/apply方法最大的作用就是能改變this關鍵字的指向.
Obj.method.apply(AnotherObj,arguments);
var name="XL";var Person={ name:"xl", showName:function(){ console.log(this.name); }}Person.showName.call(); //輸出 "XL"//這裡call方法裡面的第一個參數為空白,預設指向window。//雖然showName方法定義在Person對象裡面,但是使用call方法後,將showName方法裡面的this指向了window。因此最後會輸出"XL";
funtion FruitA(n1,n2){ this.n1=n1; this.n2=n2; this.change=function(x,y){ this.n1=x; this.n2=y; }} var fruitA=new FruitA("cheery","banana");var FruitB={ n1:"apple", n2:"orange"};fruitA.change.call(FruitB,"pear","peach"); console.log(FruitB.n1); //輸出 pearconsole.log(FruitB.n2);// 輸出 peach
FruitB調用fruitA的change方法,將fruitA中的this綁定到對象FruitB上。
JavaScript中的this關鍵字