为什么_this.
无效,this.
正在运作。
我认为_this=this
的重点在于提供一种机制来调用对象函数,你有一个"保证"引用回实例化对象,因为它现在位于对象函数的闭包内,以模仿传统的类行为。我读了很多关于范围的文章,出于某些原因,我还没有看到它。我错过了什么?
var PersonClass = function PersonClass(_name, _age) {
_this=this;
this.name=_name;
this.age=_age;
console.log("created "+this.name+":"+this.age);
function changeAge(num) {
console.log("changing age for:" + _this.name);
_this.age=num;
}
PersonClass.prototype.changeAge=changeAge;
PersonClass.prototype.getAge=function() {
console.log(_this.name+":"+_this.age);
return _this.age;
};
PersonClass.prototype.getAge2=function() {
console.log(this.name+":"+this.age);
return this.age;
};
};
// comments indicate what value is displayed in console
var john=new PersonClass("john",1); // john:1
var sue=new PersonClass("sue",2); // sue:2
john.getAge(); // sue:2
john.getAge2(); // john:1
john.changeAge(10); // sue
sue.getAge(); // sue:10
sue.getAge2(); // sue:10
john.getAge(); // sue:10
john.getAge2(); // john:1
答案 0 :(得分:2)
致电时
new PersonClass()
第一次创建原型方法。
致电时
new PersonClass()
第二次,原型方法被替换,现在他们在关闭范围内有 last _this 。
因此,将原型方法移到构造函数之外。
答案 1 :(得分:2)
问题是您的内部函数的scope
未解析为this
,因此,他们失去了对new PersonClass()
实例创建的范围的所有引用。 bind
方法将内部函数的scope
解析为父函数类的this
。
var PersonClass = function PersonClass(_name, _age)
{
var _this=this;
this.name=_name;
this.age=_age;
console.log("created "+this.name+":"+this.age);
this.changeAge = function(num)
{
console.log("changing age for:" + _this.name);
_this.age = num;
}.bind(this);
this.getAge = function()
{
console.log(_this.name+":"+_this.age);
return _this.age;
}.bind(this);
this.getAge2 = function()
{
console.log(this.name+":"+this.age);
return this.age;
};
};
// comments indicate what value is displayed in console
var john = new PersonClass("john",1); // john:1
var sue = new PersonClass("sue",2); // sue:2
john.getAge(); // sue:2
john.getAge2(); // john:1
john.changeAge(10); // sue
sue.getAge(); // sue:10
sue.getAge2(); // sue:10
john.getAge(); // sue:10
john.getAge2(); // john:1
是的,那就做了。
嘿,看,它的作品! Here's the updated Fiddle 仅提供有关bind
让我说我有object
:
var myObj = {};
我们为object
分配了一个属性:
myObj.test_property = "Hello World!";
我们可以通过bind
和this
从其他媒体资源中访问该媒体资源。
让我们说我们制作另一个function
:
myObj.test_func = function()
{
alert(this.test_property);
}.bind(myObj);
等等你猜这会吗?
由于bind
方法,this
的范围已解析为myObj
。
因此,this.test_property
等于myObj.test_property
,保留范围。
让我们走得更远......
我们将宣布另一项功能:
myObj.test_func2 = function(val)
{
this.test_property = val;
}.bind(myObj);
现在,让我们运行测试:
myObj.test_func();
myObj.test_func2("Hello Dude");
myObj.test_func();
如您所见,test_func
和test_func2
共享相同的范围。
Here's a JSFiddle illustrating everything I've said about bind
答案 2 :(得分:2)
您的代码存在很多问题。
_this=this;
创建全局变量window._this
。
使用像jshint这样的工具来避免这种错误。
PersonClass.prototype
不应在构造函数中使用。您正在混合两种不同的对象创建模式。在构造函数中,你应该使用类似
this.getAge2 = function(){...}
不一定是一个错误,但是对于你的示例代码将此绑定到_这不是必需的。这仅适用于未在您创建的对象上调用函数的情况,例如,使用window.setTimeout(john.getAge, 100)
这会导致getAge函数在调用时从john对象中解除绑定。
这里的代码包含所讨论的更改(这并不是说我推荐这种模式):
var PersonClass = function PersonClass(_name, _age) {
var _this=this;
this.name=_name;
this.age=_age;
console.log("created "+this.name+":"+this.age);
function changeAge(num) {
console.log("changing age for:" + _this.name);
_this.age=num;
}
this.changeAge=changeAge;
this.getAge=function() {
console.log(_this.name+":"+_this.age);
return _this.age;
};
this.getAge2=function() {
console.log(this.name+":"+this.age);
return this.age;
};
};
var john=new PersonClass("john",1); // john:1
var sue=new PersonClass("sue",2); // sue:2
john.getAge(); // john:1
john.getAge2(); // john:1
john.changeAge(10); // john
sue.getAge(); // sue:2
sue.getAge2(); // sue:2
john.getAge(); // john:10
john.getAge2(); // john:10
window.setTimeout(john.getAge, 200); //john:10
window.setTimeout(john.getAge2, 400); // incorrect