javascript – node.js中类实例之间的共享数组
内容导读
互联网集市收集整理的这篇技术教程文章主要介绍了javascript – node.js中类实例之间的共享数组,小编现在分享给大家,供广大互联网技能从业者学习和参考。文章包含4122字,纯文字阅读大概需要6分钟。
内容图文
![javascript – node.js中类实例之间的共享数组](/upload/InfoBanner/zyjiaocheng/804/6030c16ed4544f5aa4f8abc08fc473ff.jpg)
我在node.js中有一个奇怪的问题:
person.js
var Person;
Person = (function() {
Person.prototype.name = "";
Person.prototype.friends = [];
function Person(name) {
if (name) {
this.name = name;
}
}
Person.prototype.sayHello = function() {
return console.log("Hello, my name is " + this.name + " and I have " + this.friends.length + " friends");
};
Person.prototype.addFriend = function(name) {
this.friends.push(name);
};
return Person;
})();
module.exports = Person;
factory.js
var Person = require('./Person.js');
module.exports = function(name) {
return new Person(name);
};
index.js
factory = require('./factory');
tyrion = factory("Tyrion");
tyrion.addFriend("Bronn");
tyrion.sayHello();
daenerys = factory("Daenerys");
daenerys.addFriend("Illyrio");
daenerys.addFriend("Daario");
daenerys.addFriend("Barristan");
daenerys.sayHello();
tyrion.sayHello();
实际输出
Hello, my name is Tyrion and I have 1 friends
Hello, my name is Daenerys and I have 4 friends
Hello, my name is Tyrion and I have 4 friends
预期产出
Hello, my name is Tyrion and I have 1 friends
Hello, my name is Daenerys and I have 3 friends
Hello, my name is Tyrion and I have 1 friends
为什么在一个实例中添加元素会为两者添加它?看起来好友数组在实例之间“共享”.如何预防?
解决方法:
这条线
Person.prototype.friends = [];
将friends属性添加到Person原型,这使得它与使用Person构造函数创建的所有新对象共享.因此,如果您希望每个对象都有自己的朋友,则必须将friends属性添加到单个对象.
你真正想做的就是你用名字做的事情:
function Person(name) {
// friends is a property of this, the new instance object.
this.friends = [];
if (name) {
this.name = name;
}
}
在Javascript中,原型有点像其他OO语言的基类(我说有些重要的原因,我稍后会解释).当您向原型添加内容时,它将由具有该原型的所有内容共享.这就是为什么你的’sayHello’函数被添加到原型中的原因,因为你希望你的所有Person实例能够说你好.通过向原型中添加朋友,您说’我希望所有这些都由Person类型共享.’
关键是在Javascript中实际上有两个步骤可以使对象看起来像一个类的成员.第1步,创建一个原型并添加将要共享的东西,通常是方法.步骤2,在创建单个对象后,将属性添加到该对象.如果您在步骤1中添加了您想要的“实例变量”,那么您实际要做的就是创建共享的变量,就像您的方法一样,这就是您在上面所做的.
我之前说过,原型有点像基类.我有点说,因为它只是表面上的那种方式.这是一个非常重要的细节,了解它如何真正起作用将为您节省大量的麻烦和后来的困惑.
理解Javascript的一个重要事情是它没有类.因此,与其他语言不同的是,有一种称为“类”的东西,另一种称为“实例”,Javascript只有对象.即使看起来一件事是一个类,另一件事是该类的一个实例,它只是外观.如果你没有注意,那个外表可以欺骗你.
Javascript使用了一种称为“原型继承”的东西,这是一种很长的说法,即对象继承自其他对象.把它想象成一个链条.如果你有tyrion并且你访问sayHello,就像这样:
tyrion.sayHello()
Javascript查看名为sayHello的属性的tyrion对象.它没有找到它,所以它然后查找了tyrion的原型,如果有的话,它会查看它是否有一个名为sayHello的属性.这次它找到它,确定它是一个函数,然后调用它,告诉它在函数中tyrion应该是’this’.如果它是用javascript编写的,它看起来像这样:
function find_property(original_obj, property_name) {
var found_prop = undefined;
var current_obj = original_obj;
// we keep searching until we either have a property or we run out of
// places to look.
while(found_prop == undefined && current_obj != undefined) {
// does the object we are looking at have it's own property with that name?
if ( obj.hasOwnProperty(property_name) ) {
// yes, so we can set found_prop
found_prop = obj[property_name];
} else {
// no, we have to look at the next prototype up the chain.
current_obj = current_obj.__proto__;
}
}
return found_prop;
}
var sayhello = find_property(tyrion, 'sayHello');
if (typeof sayhello == 'function') {
sayhello.call(tyrion);
}
这是一个非常重要的细节,因为每个原型只是一个对象,可以随时修改.这意味着即使在使用它作为原型创建了许多其他对象之后,您也可以修改原型对象,当您这样做时,您实际上是向在其层次结构中某处使用该原型的每个对象添加内容.对于来自语言的人来说,这是一个非常意外的行为,这些语言不允许您在创建后更改“类”.
在你的情况下,你正在修改原型的朋友列表,因为没有一个孩子有他们自己的’朋友’属性,当javascript去寻找’朋友’时,它总是找到原型上的那个.
希望有所帮助,并为您节省一些麻烦.如果你想进一步了解它,Douglas Crockford的’Javascript:The Good Parts’是一本很好的书.
内容总结
以上是互联网集市为您收集整理的javascript – node.js中类实例之间的共享数组全部内容,希望文章能够帮你解决javascript – node.js中类实例之间的共享数组所遇到的程序开发问题。 如果觉得互联网集市技术教程内容还不错,欢迎将互联网集市网站推荐给程序员好友。
内容备注
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 gblab@vip.qq.com 举报,一经查实,本站将立刻删除。
内容手机端
扫描二维码推送至手机访问。