this_原型鏈_繼承

this 相關(guān)問題

apply、call 、bind有什么作用,什么區(qū)別?

  1. apply
    語法格式:function.apply(this, [arguments])
    參數(shù)this是在函數(shù)function運(yùn)行時(shí)指定的this值,在調(diào)用function時(shí)可以為它指定一個(gè)this對(duì)象,this指的就是調(diào)用function的對(duì)象(函數(shù)執(zhí)行時(shí)所在的上下文),然后在這個(gè)上下文中調(diào)用該函數(shù),作用就是以對(duì)象的方法的形式來調(diào)用函數(shù),如:
f.apply(o);
類似于
o.method=f; //f函數(shù)類似于o對(duì)象的臨時(shí)方法
o.method();//調(diào)用它

apply方法的作用和call方法類似,只有一個(gè)區(qū)別,call方法傳入的是參數(shù)列表,而apply方法傳入的是一個(gè)包含多個(gè)參數(shù)的數(shù)組。
如:

f.apply(o,[1,2]);
f.call(o,1,2);

bind的作用:
bind方法主要是將函數(shù)綁定到某個(gè)對(duì)象上,當(dāng)在函數(shù)f()上調(diào)用bind方法并傳入一個(gè)對(duì)象o作為參數(shù),這個(gè)方法將返回一個(gè)新的函數(shù)。調(diào)用新函數(shù)時(shí),會(huì)把原始函數(shù)當(dāng)做對(duì)象o的方法調(diào)用,傳入新函數(shù)的實(shí)參都會(huì)傳到原始函數(shù),

function f(y){
   return this.x+y;
}
var o={
   x:1
}
var g=f.bind(o);//通過g(x)來調(diào)用o.f(x);
g(2)  //3

bind方法將f函數(shù)內(nèi)部的this綁定到o對(duì)象上,當(dāng)調(diào)用f函數(shù)時(shí),f函數(shù)會(huì)以創(chuàng)建它時(shí)傳入 bind()方法的第一個(gè)參數(shù)作為 this,傳入 bind() 方法的第二個(gè)以及以后的參數(shù)加上綁定函數(shù)運(yùn)行時(shí)本身的參數(shù)按照順序作為原函數(shù)的參數(shù)來調(diào)用原函數(shù)。
三者比較:
apply 、 call 、bind 三者都是用來改變函數(shù)的this對(duì)象的指向的;
apply 、 call 、bind 三者第一個(gè)參數(shù)都是this要指向的對(duì)象,也就是想指定的執(zhí)行上下文;
apply 、 call 、bind 三者都可以在this后傳參數(shù);
bind 是返回新的函數(shù),可以之后調(diào)用;apply 、call 則是立即調(diào)用 。

以下代碼輸出什么?

var john = { 
  firstName: "John" 
}
function func() { 
  alert(this.firstName + ": hi!")
}
john.sayHi = func
john.sayHi()  //John hi!

下面代碼輸出什么,為什么

func() 
function func() { 
  alert(this)
}
//window,因?yàn)閠his指向的函數(shù)運(yùn)行時(shí)的環(huán)境,現(xiàn)在func的執(zhí)行上下文是window,所以輸出window.

下面代碼輸出什么

document.addEventListener('click', function(e){
    console.log(this);
    setTimeout(function(){
        console.log(this);
    }, 200);
}, false);

1.#document,因?yàn)閏lick方法是在document的環(huán)境中被調(diào)用的,所以this指向document。
2.window對(duì)象,setTimeout函數(shù)是在click事件結(jié)束之后才執(zhí)行的,所以它的執(zhí)行環(huán)境是window,this指向的是window

下面代碼輸出什么,why

var john = { 
  firstName: "John" 
}

function func() { 
  alert( this.firstName )
}
func.call(john) //John,因?yàn)閏all的第一個(gè)參數(shù)傳入的時(shí)調(diào)用func的上下文,所以func函數(shù)在john的執(zhí)行上下文中,this指的john.

以下代碼有什么問題,如何修改

var module= {
  bind: function(){
    $btn.on('click', function(){
      console.log(this) //this指什么
      this.showMsg();
    })
  },
  
  showMsg: function(){
    console.log('饑人谷');
  }
}
改:
  var module= {
        bind: function(){
            var self=this;
            $('.btn').on('click', function(){
                console.log(this) //this指什么,指的是btn,
                self.showMsg(); //
            })
        },
        showMsg: function(){
            console.log('饑人谷');
        }
    }
    module.bind();//饑人谷
  在click事件中的this指的都是$btn.而在這個(gè)事件的執(zhí)行上下文中沒有
showMsg()函數(shù),所以調(diào)用的時(shí)候會(huì)提示showMsg()is not a function。
showMsg()在bind的作用域里,所以把指向bind的this保存到self中,在click事件中使用就不會(huì)報(bào)錯(cuò)了。

原型鏈相關(guān)問題

有如下代碼,解釋Person、 prototype、proto、p、constructor之間的關(guān)聯(lián)

function Person(name){
    this.name = name;
}
Person.prototype.sayName = function(){
    console.log('My name is :' + this.name);
}
var p = new Person("若愚")
p.sayName();

如圖:
??Person是一個(gè)構(gòu)造函數(shù),也是一個(gè)對(duì)象,函數(shù)內(nèi)部定義了name屬性,和自身帶有的prototype屬性,所有實(shí)例Person的實(shí)例都會(huì)生成這些屬性。
??p是構(gòu)造函數(shù)Person的一個(gè)實(shí)例,所以p具有name的屬性。因?yàn)槊總€(gè)構(gòu)造函數(shù)的實(shí)例都會(huì)有一個(gè)隱藏的屬性proto,指向構(gòu)造函數(shù)的prototype屬性,所以p里的proto指向Person中的prototype。
??Person.prototype是Person的原型對(duì)象,里面定義了一個(gè)sayName,所以Person的實(shí)例都可以調(diào)用該方法。prototype對(duì)象有一個(gè)constructor屬性,默認(rèn)指向prototype對(duì)象所在的構(gòu)造函數(shù),所以圖中的constructor就指向構(gòu)造函數(shù)Person.因?yàn)樵蛯?duì)象也是對(duì)象,所以Person.prototype中的proto就指向Person.prototype的原型。

Paste_Image.png

上例中,對(duì)對(duì)象 p可以這樣調(diào)用 p.toString()。toString是哪里來的? 畫出原型圖?并解釋什么是原型鏈。

對(duì)象p的proto指向的是構(gòu)造函數(shù)Person的原型對(duì)象,Person的原型對(duì)象也是個(gè)對(duì)象,也有自己的原型對(duì)象,這個(gè)原型對(duì)象就指Object.prototype,Object.prototype就有toString()這個(gè)方法。當(dāng)一個(gè)對(duì)象調(diào)用一個(gè)方法時(shí),會(huì)先在內(nèi)部屬性找,如果找不到,就到它的原型去找,如果還是找不到,就到原型的原型去找。如果直到最頂層的Object.prototype還是找不到,則返回undefined。

原型鏈:

對(duì)象的屬性和方法,有可能是定義在自身,也有可能是定義在它的原型對(duì)象。由于原型本身也是對(duì)象,又有自己的原型,所以形成了一條原型鏈。


未命名文件.png

對(duì)String做擴(kuò)展,實(shí)現(xiàn)如下方式獲取字符串中頻率最高的字符

  String.prototype.getMostOften=function(){
            var obj={};
         for(var i=0;i<this.length;i++){
              if(obj[this[i]]){
                  obj[this[i]]++;
              }else{
                  obj[this[i]]=1;
              }
         }
         var index;
          var max=0;
        for(var key in obj){
            if(obj[key]>max){
                max=obj[key];
                index=key;
            }
        }
        return "出現(xiàn)最多的字是"+index+"次數(shù)是"+max;
    }
    var str = 'ahbbccdeddddfgg';
    var ch = str.getMostOften();
    console.log(ch);//出現(xiàn)最多的字是d次數(shù)是5

instanceOf有什么作用?內(nèi)部邏輯是如何實(shí)現(xiàn)的?

instanceof運(yùn)算符返回一個(gè)布爾值,判斷對(duì)象是否是某個(gè)構(gòu)造函數(shù)的實(shí)例。
instanceof運(yùn)算符的左邊是實(shí)例對(duì)象,右邊是構(gòu)造函數(shù)。它會(huì)檢查右邊構(gòu)建函數(shù)的原型對(duì)象,是否在左邊對(duì)象的原型鏈上:

obj instanceof cls
function _instanceof(obj, cls) { 

var p = obj.__proto__, cp = cls.prototype; 
while(p) { 
if(p === cp) return true; 
p = p.__proto__; 
} 
return false; 
} 

繼承相關(guān)問題

繼承有什么作用?

1.實(shí)現(xiàn)代碼復(fù)用,減少內(nèi)存消耗。
2.可以覆蓋父類的屬性,可以實(shí)現(xiàn)代碼的擴(kuò)展。

下面兩種寫法有什么區(qū)別?

//方法1
function People(name, sex){
    this.name = name;
    this.sex = sex;
    this.printName = function(){
        console.log(this.name);
    }
}
var p1 = new People('饑人谷', 2)

//方法2
function Person(name, sex){
    this.name = name;
    this.sex = sex;
}

Person.prototype.printName = function(){
    console.log(this.name);
}
var p1 = new Person('若愚', 27);

第一種方法中的printName是函數(shù)自身的屬性,每new一個(gè)Person的實(shí)例就會(huì)開辟一塊內(nèi)存存儲(chǔ)printName函數(shù),內(nèi)存消耗較大。
第二種方法把printName作為Person.prototype屬性,Person的所有實(shí)例的proto都指向同一個(gè)原型對(duì)象,所有實(shí)例都共用這個(gè)方法,可以節(jié)約內(nèi)存。

Object.create 有什么作用?兼容性如何?

Object.create()方法用于創(chuàng)建一個(gè)新的對(duì)象,其中傳入的參數(shù)是該對(duì)象的原型,
如:

var obj1={
   x:1
}
var obj2=Object.create(obj1)//所以obj2就繼承了obj1的屬性x了

兼容性:

Paste_Image.png

hasOwnProperty有什么作用? 如何使用?

對(duì)象hasOwnProperty()方法用于檢測給定的名字是否是對(duì)象自有的屬性,對(duì)于繼承的屬性它將返回false.
使用方法:

var o={
 x:1
}
o.hasOwnProperty(“x”)  //true,因?yàn)閛對(duì)象有一個(gè)自有屬性x
o.hasOwnProperty(“y”)  //false,因?yàn)閛對(duì)象沒有自有屬性y
o.hasOwnProperty(“toString”)  //false,因?yàn)閠oString是繼承屬性。

如下代碼中call的作用是什么?

function Person(name, sex){
    this.name = name;
    this.sex = sex;
}
function Male(name, sex, age){
    Person.call(this, name, sex);    //這里的 call 有什么作用
    this.age = age;
}

函數(shù)實(shí)例的call方法,可以指定函數(shù)內(nèi)部this的指向,并在所指定的作用域中,調(diào)用該函數(shù)。Person.call(this,name,age) 的 意思就是使用 Person構(gòu)造函數(shù)的實(shí)例在this對(duì)象(也就是當(dāng)前的執(zhí)行上下文,Male的作用域)下執(zhí)行,那么 Male就有了Person的所有屬性和方法,實(shí)現(xiàn)了繼承。

補(bǔ)全代碼,實(shí)現(xiàn)繼承

 function Person(name, sex){
        this.name=name;
        this.age=sex;
    }

    Person.prototype.getName = function(){
       console.log(this.name)
    };

    function Male(name, sex, age){
        Person.call(this,name,sex);
        this.age=age;
    }

    Male.prototype.getAge = function(){
          console.log(this.age);
    };
    Male.prototype=Object.create(Person.prototype);
    var ruoyu = new Male('若愚', '男', 27);
    ruoyu.getName();
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • 1: apply、call 、bind有什么作用,什么區(qū)別 call 和 apply 都是為了改變某個(gè)函數(shù)運(yùn)行時(shí)的...
    高進(jìn)哥哥閱讀 352評(píng)論 0 0
  • 1. this2.原型鏈-instanceof實(shí)現(xiàn)3.繼承的實(shí)現(xiàn) ** this 相關(guān)問題 ** ** 1、 ap...
    饑人谷_阿靖閱讀 413評(píng)論 0 0
  • 1. apply、call 、bind有什么作用,什么區(qū)別? call ,apply的作用:調(diào)用一個(gè)函數(shù),傳入函數(shù)...
    Rising_suns閱讀 433評(píng)論 0 0
  • 1:apply、call 、bind有什么作用,什么區(qū)別 call 和 apply 都是為了改變某個(gè)函數(shù)運(yùn)行時(shí)的上...
    進(jìn)擊的前端_風(fēng)笑影閱讀 312評(píng)論 0 0
  • 一、this 相關(guān)問題 知乎上關(guān)于this的解答 this 的值到底是什么?一次說清楚 this 的工作原理在js...
    66dong66閱讀 644評(píng)論 0 0

友情鏈接更多精彩內(nèi)容