JavaScript权威指南7(三) 第六章 Object Prototype Methods

Object 对象
对象不仅仅是简单的字符串到值的映射,除了维护自己的属性集,JavaScript对象还继承另一个对象的属性,即它的原型。对象的方法通常是继承的属性,而这种原型继承是JavaScript的一个关键特性。

Prototypes
所有通过对象字面量创建的对象都具有一个原型对象,并可以通过JavaScript代码Object.prototype获得对原型对象的引用。通过关键字new和构造函数调用创建的对象的原型就是构造函数的prototype属性的值。因此,同使用{}创建对象一样,通过new Object()创建的对象也继承自Object.prototype。同样,通过new Array()创建的对象的原型就是Array.prototype,通过new Date()创建的对象的原型就是Date.prototype。几乎所有对象都有原型,但只有相对较少的对象具有原型属性。正是这些具有原型属性的对象定义了所有其他对象的原型。
没有原型的对象为数不多,Object.prototype就是其中之一,它不继承任何属性。其他原型对象都是普通对象,普通对象都具有原型。大部分的内置构造函数(以及大部分自定义的构造函数)都具有一个继承自Object.prototype的原型。
例如:Date.prototype的属性继承自Object.prototype,因此new Date()对象的属性同时继承自Date.prototype和Object.prototype。这一系列链接的原型对象就是所谓的原型链(prototype chain)

Inheritance
假设要查询对象o的属性x。如果o中不存在x名称的自由属性,那么将会继续在o的原型对象中查询属性x。如果原型对象中也没有x,但这个原型对象也有原型,那么继续在这个原型对象的原型上执行查询,直到找到x或者查找到一个原型是null的对象为止。对象的原型属性构成了一个"链",通过这个"链"可以实现属性的继承。

let o = {}; // o从对象继承对象原型
o.x = 1; // 现在有了自己的属性x
let p = Object.create(o); // p从o和对象继承原型
p.y = 2; // 并且有了自己的属性
let q = Object.create(p); // q继承p
q.z = 3; // 有自己的属性z
let f = q.toString(); // toString是从对象继承原型
q.x + q.y; // 3 x和y是从o和p继承的

现在假设给对象o的属性x赋值,如果o中已经有属性x(这个属性不是继承来的),那么这个赋值操作只改变这个已有属性x的值,否则,赋值操作给o添加一个新属性x。如果之前o继承自属性x,那么这个继承的属性就被新创建的同名属性覆盖了。
属性赋值操作检查原型链只是判断是否允许赋值操作。例如,如果o继承自一个只读属性x,那么赋值操作时不允许的。如果允许属性赋值操作,它也总是在原始对象上创建属性或对已有属性赋值,而不会去修改原型链。在JavaScript中,只有在查询属性时才会体会到继承的存在,而设置属性则和继承无关,这是JavaScript的一个重要特性。

let unitcircle = {r:1};
let c = Object.create(unitcircle);
c.x = 1;
c.y = 1;
c.r = 2;
console.log(unitcircle.r); // 1 原型不受影响

属性赋值要么失败,要么创建一个属性,要么在原始对象中设置属性。但有一个例外,如果o继承自属性x,而这个属性是一个具有setter方法的存取器属性,那么这时将调用setter方法而不是给o创建一个属性x。需要注意的是,setter方法是由对象o调用的,而不是定义这个属性的原型对象调用的。因此如果setter方法定义任意属性,这个操作只是针对o本身,并不会修改原型链。

Property Enumeration Order
ES6正式定义元素的自有属性的枚举顺序
Object.keys()
Object.getOwnPropertyNames()
Object.getOwnPropertySymbols()
Reflect.ownKeys()
JSON.stringify()
受它们自身是否是不可枚举属性列表或者属性字符串或者Symbol影响。

Object Methods
toString() 方法没有实参,它将返回一个表示调用这个方法的对象值的字符串。在需要将对象转换为字符串的时候,都会调用这个方法。
toLocaleString() 对象都包含这个方法,返回一个表示这个对象的本地化字符串。Object中默认的toLocaleString方法并不做任何本地化自身的操作,仅调用toString方法返回对应值。Date和Number类对toLocaleString方法做了定制,可以用它对数字,日期和时间做本地化的转换。
valueOf() 与toString类似,当JavaScript需要将对象转为某种原始值而非字符串的时候才会调用它,尤其是转换为数字的时候。
toJSON() Object.prototype实际上没有定义toJSON方法,但对于需要执行序列化的对象来说,JSON.stringify()方法会调用toJSON方法。如果在待序列化的对象中存在这个方法,则调用它,返回值即是序列化的结果,而不是原始对象。

所有JavaScript的非原始值都是对象,包括数组和函数。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值