改变this指向
做个记录,说一下我的理解。
1.7是一个基本数据类型number类型
2.bar.call(7),相当于用7的对象去调用bar函数,但是7是基本类型,为什么可以调用。因为在调用的时候自动变为包装类了,类似于 let a = new Number(7)
3.Object.prototype.toString.call(this),根据2的理解,是一个Number类型的对象调用bar方法,那么这里的this就是一个Number对象。
你好,你的理解没有问题,可能是其他问题导致出现了这样的结果。附上图:
get获取的是modulus()这个方法,也就是最上边那个,你可以试试改改函数名,是一样的。
这个意思大致是:在o这个对象上添加一个叫做modulus的方法,这个方法调用modulus()这个方法
可以的,不过这里不设置writable属性,就是默认不可写,writable:false
第一个MyClass没有写return返回值,所以调用构造器的时候,就将this作为返回值
你代码都写错了,console.log(o.f())才是调用函数,结果是23
写一下我的理解
toString()方法是没有参数的.
相当于
var o ={
toString : function(){
console.log("无论你传给我什么我都输出这行字.")
}
};
你用到函数toString()的时候,只能o.toString()
无论是o.toString('99999'),还是o.toString('88888'),对函数输出的结果 没有影响
所以Object.prototype.toString(this) , 这样写的话对输出结果是没有影响的, 就相当与Object本身在调用他自己的toString()方法
但是加上call()方法呢, Object.prototype.toString.call(this), 这实际相当于是用this对象来调用Object的toString()方法
那么怎么确定this的指向呢?
由于bar()函数同样没有参数 , 所以要用call()方法来传入this的值
如果你这样定义bar函数
function bar(a) {
console.log(Object.prototype.toString.call(a));
};
那在调用的时候就不需要bar.call()了,直接bar(56789)就行了
可能还有不对的地方, 能力有限啊
因为o对象的本身是没有定义add方法的,在这个案例中,add()方法定义在window上,所以就算你在外面add(5,7),这样去执行,其实还是在window对象上调用的add,相当于window.add(5,7);只是window上调用方法和属性的时候,前面的window可以默认不用写而已。
这就存在一个问题,o对象内部是没有add方法的,但是我想让它借用window对象的这个方法去实现我要的功能怎么办呢?这个时候就要用到call和apply。具体操作就是老师讲的:需要调用的函数名.call(需要调用这个方法的对象,参数1,参数2,...,参数N);其本质说白了就是将这个方法强拉硬拽地拖到o对象上,假装是o名义下的方法去为o对象服务和工作。
那这样有啥好处呢?好处就是方便重用和继承,这个后面OOP的章节肯定会讲。每当你定义一个函数,其实是在内存里开辟了一块空间来存放这个函数对象的,哪怕这两个函数每个字都一样,也是两个不同的对象,如果外部有了一个add函数,你为了让它能执行o对象里面的方法,又在o对象里在写一个o.add;那么无疑是很费内存的,也不方便维护,项目小没啥说法,项目大了维护起来简直是辣眼睛。。。
[object Number]
也就是bar调用7这个值作为参数,this指向函数调用的元素,而tostring.call调用该元素,返回元素属性,yeah
1.当函数作为对象的方法调用时,this指向该对象。
2.当函数作为淡出函数调用时,this指向全局对象(严格模式时,为undefined)
3.构造函数中的this指向新创建的对象
4.嵌套函数中的this不会继承上层函数的this,如果需要,可以用一个变量保存上层函数的this。
再总结的简单点,如果在函数中使用了this,只有在该函数直接被某对象调用时,该this才指向该对象。
在body内的脚本会在页面加载时执行,body外的会在调用时执行
我是这样理解的:bar.call(7) 结果this=7
然后执行函数内部的Object.prototype.toString.call(this) 就相当于object.prototype.toString.call(7) 相当于 7.prototype.toString();
或 这样理解bar.call(7) 为7.bar()
Object.prototype.toString.call(this) 为this.prototype.toString(); 7.bar() 调用时,this指向7,所以为7.prototype.toString();
个人理解 仅供参考
bar.call(7)是利用call改变函数bar()中的this的指向,且立即执行函数bar();由于this执行对象为7,执行语句变为“console.log(Object.prototype.toString.call(7)”,所以结果显示“[Object Number]”
关于add.call(o,1,10);你可以理解为,对象o中有了add这个方法,即:
var o{
a:1,
b:3,
// 在对象o中新增加了
function add(c,d){
return this.a +this.b+c +d;
}
return this.a +this.b+c +d
}
此时的a,b就是1,3;而1,10就是c,d
property
我也没找到,楼主你找到了吗?
看如何调用啦,如果当做普通的函数直接去调用,如:MyClass(); 它的this指向window
如果是当做构造函数去调用,如:new MyClass();它的this就会指向新创建的对象实例
我怎么感觉像是一种类的继承,不过基类的this竟然能够获取到子类的属性 - -。
使用小括号的时候,一般是要调用函数的时候。比如,这里有一个函数,
var f = function(){
return "aa";
}
// 当调用这个函数的时候,可以写成:
f();
如果单纯只是在一个函数中调用另一个函数是没什么多大区别,apply / call 的最大作用就是改变上下文 比如说: var name = "张三"; //在全局里定义函数func1 function getName(){ return this.name; } //在对象里定义函数func2 var obj = { name:"李四", showName:function(){ return getName.apply(this); //在showName里调用getName,并将this从window改变为obj } }; console.log(obj.showName()); //"李四"
o.f()为什么会输出37?
对象o调用了方法f(), 然而f()就是要返回当前对象的属性a, 而当前对象是o, o有一个属性a的值是37, 所以打印37;
o是对象吗?是;f是函数吗?是;
为什么可以对象.函数()?
猜测题主的意思是为什么要在函数名后面加小括号吧,如果不是请指正。对象.函数(), 这种形式表示要执行函数。函数分为两种状态:定义状态和运行状态。而调用函数让它运行的时候要用到这种格式。
call方法的第一个实参就是要调用函数的母对象,他是调用上下文,bar函数里面的this指向的就是Number 7
接上边:this通常是指向当前函数的拥有者,所以当前方法 f 的拥有者是 对象o,所以 o.f() 时执行 f() ,this 指向 o, o.prop=37;
创建了一个对象p,并且 p的原型指向 o
1)隨時可以調用,但是不同的地方調用會有不同的反回值。
2)有時候是為了提高可讀性。
在網頁上,直接開啟console輸入
this; //window var aaa = { bbb: 123, ccc: function(){ this; //aaa return this; }, ddd: function fff(){ var eee = this; return eee; } }; aaa.ccc(); //aaa aaa.ddd(); //aaa var zzz = aaa.ddd(); zzz.bbb; //123 zzz.bbb = 456; aaa.bbb; //456 zzz.bbb; //456
o.f指向的是函数对象, o.f()返回函数执行的结果
o.__proto__ == MyClass.prototype //true
加括号就是调用函数了,这里只是把o.f指向了independent函数的引用,下面的o.f()才是真正的调用函数