javascript:属性究竟是如何从原型(prototype)继承的?

标签 javascript inheritance

考虑一段代码

function F(){
   this.p=10;
}
F.prototype.newProp='some value';
var f1=new F(), f2=new F();

alert(f1.__proto__==f2.__proto__); //returns true. implies f1 and f2 share same instance of prototype object 

f1.newProp='new value'; //changing the value of inherited property
alert(f2.newProp); //returns 'some value' 

好的,现在问题是 f1 和 f2 是否共享同一个 [[prototype]] 对象实例 而如果 javascript 中的属性检索通过沿着原型(prototype)链进行遍历

因此,如果我更改共享 [[prototype]] 对象的属性(在本例中为 newProp)的值, 为什么它也没有反射(reflect)在 f2 中, 因为 f1.proto==f2.proto (这意味着它是同一个对象) 那么为什么改变 f1 的 newProp 不会改变 f2 的 newProp(两者都继承自同一个原型(prototype)对象,不是吗?)

令人惊讶的是,更改 f1.proto.newProp 反射(reflect)了检索“f1.newProp”时的更改

那么,f1.newProp 和 f1.proto.newProp 是不同的属性吗?

我认为在 javascript 中查找属性是通过在原型(prototype)链中连续查找更高层来实现的。

如果我的问题听起来很幼稚,我很抱歉,但我无法理解:

如果 1) f1.proto==f2.proto//真!意味着对象 f1 和 f2 都引用相同的 [[prototype]] 对象,它们从中继承

如果

2) 在其原型(prototype)中搜索未在对象中找到的属性。

那为什么改变 f1.newProp 也没有反射(reflect)在 f2.newProp 中?因为两者都有共同的 [[prototype]] 属性,如第 (1) 点所示

是否原型(prototype)对象的属性被单独复制到 f1 和 f2 中。 ? 但这违反了第(2)点[在对象中找不到时查找原型(prototype)链的属性]

请解释这里的矛盾。非常感谢你:)

==================编辑================

谢谢@jfriend00 的回复。

但假设我有这段代码

function Person(name, age){      
    this.name=name;
    this.age=age;
    alert("obj created:"+name);
}
function Employee(name,age,eid){
    this.base=Person;
    this.base(name,age);
    this.eid=eid;
}
Employee.prototype=new Person;

var ob1=new Employee('name1',23,100);
var ob2=new Employee('name2',24,101);

这里也是,显然是ob1.proto==ob2.proto 但如果我没记错的话,每个员工实例都有 2 个对象

1 是 employee 对象本身,只有 1 个属性 eid(和其他一个 base func)

第二个是 Person 对象,它被 employee 对象的 [[prototype]] 属性引用。这个对象有 name 和 age 属性.. 因此,employee obj 实际上从其 [[prototype]] Person 对象中存储和检索姓名和年龄。 我说得对吗?

如果是这样,并且由于 ob1.proto==ob2.proto,那么我们如何才能存储两个对象的唯一名称和年龄?

我的意思是,这里似乎每个员工都有一个原型(prototype)对象。 如果你能解释一下,非常感谢你:)

还有一个查询是:

为什么上面的代码即使注释掉了也能正常工作

Employee.prototype=new Person;

在上面的行中,从而打破了 2 个 objs 之间的链接。继承仍然有效只是因为我已将 Person 函数声明为 Employee 的属性并从中调用 Person 。 这是怎么回事 谢谢:)

最佳答案

一旦设置了 f1.newProp = 'new value',它就不再是在原型(prototype)上设置 newProp,而是在 f1 上设置对象本身。试试这个,你会看到:

var f1=new F(), f2=new F();
console.log(f1.hasOwnProperty('newProp')); // returns false, because it is from prototype
f1.newProp = 'new value';
console.log(f1.hasOwnProperty('newProp')); // returns true

关于javascript:属性究竟是如何从原型(prototype)继承的?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27033151/

相关文章:

javascript - 为什么满足if条件后还要进入else部分?

javascript - 创建弹出警报

javascript - 使用 laravel 对象在 vue 模板中动态图像的数据绑定(bind)样式

c++ - 为什么要检查 Base 是 Derived 的私有(private)基还是 protected 基?

c++ - 在 C++11 中对派生类使用基类运算符

php - 从基类调用继承类的父方法

javascript - 如何获取当前范围内定义的所有变量的列表?

javascript - react 导航 bottomTabNavigator "createRouter is not a function"

ruby-on-rails - 继承的 Active Record 类的 link_to 问题

java - 带有文件名的子类中出现奇怪的错误