JS之对象

1.声明对象:

其中的name那可以加引号也可以不加。10那儿会自动转为字符串。也可以用new Object()声明

2.数据属性

通过defineProperty为对象中的属性配置数据属性,注:对象中的某一个属性进行配置后并不会影响其他属性的数据属性,比如num中的writable等设为false后,其他属性不会受到影响(所以只是对当前的属性进行设置)。如果b最开始没有设置num属性,在defineProperty中设置num属性,会主动为b添加一个num属性,并且默认为false。如下图:

上方代码并没有设定age属性,输出结果默认false,并且value为undefined。

注:之后写代码尽量加上引号,会出现属性undefined的报错

 

3.访问器属性

类似于上面的数据属性,访问器属性只有一个set函数和一个get函数,前者用于负责决定如何处理函数,后者用于负责返回有效值。如:

和上面差不多,这里是制定了get和set的方法,get就是在读取的时候和执行到,set是在给属性赋值时执行。

疑问:最后两行,用book.year输出正常为2,但用book._year输出为1,不知道为什么

利用getOwnPropertyDescriptor可以读取对象属性

 

4.创建对象

4.1工厂模式

相当于创建一个函数,返回函数中创建好的对象

4.2构造函数模式

没有显式地创建对象;直接将属性和方法赋给了this对象,没有return语句

(之前总结过一篇this的博客,https://blog.csdn.net/sinat_28839863/article/details/88416772,里面有return的构造函数例子)

这里会将属性和方法添加给window对象,因为在全局中调用一个函数this总是指向Global对象,浏览器中就是window

也可以通过apply和call方法实现

 

对象的constructor属性可以标识对象类型,不过一般用instanceof。obj.constructor == Object和obj instanceof Object一样

 

4.3构造函数缺点

从上面的执行可以看出,p1和p2是不同的,然而它们各自的函数执行的功能是相同而且地址是不一样的,那为什么同样的功能要写两遍呢,也就是说虽然执行了相同的代码,但浪费了内存。

那么如何解决构造函数产生的缺点呢?

第一种(简单):

弄一个全局函数,然它们初始化时全部指向它就行了

第二种:原型模式

每个函数都有一个原型对象prototype,翻译过来就是原型类型,原型也就是最基本的那一种,类似于C和java种的static。

通过构造函数来创建那个对象实例的原型对象,从而让所有对象实例能共享包含的属性和方法。例如:

由于p1和p2所包含的实例是同一个,所以true

prototype,它默认指向一个Object空对象(也成为原型对象),原型对象中还有一个属性constructor指向函数对象(Person)

例如:来自B站一个视频,得到true

注:

1.每当代码读取某个对象的某个属性时,目标是具有给定名字的属性。搜索首先从对象实例开始,如果在对象实例中找到了这个属性,那么直接返回;如果没有找到,那么搜索prototype指向的原型对象中查找属性。所以,如果是原型对象中保存的属性就是共享的,如果普通对象中保存的属性,那么就是各自不同的属性了。

2.当给对象实例添加一个属性时,这个属性会屏蔽原型对象中保存的同名属性,并不会修改原型对象中的属性,通过delete删除实例对象中的属性可以恢复访问原型对象的属性。(实例对象的hasOwnProperty("attr")可以判断attr实例中是否有attr属性)

3.当原型对象的属性值为基本类型的数据值时,通过实例对象修改属性值从而引起原型对象的属性值发生变化的情况不会发生。当原型对象的属性值为引用类型的数据值时,通过实例对象修改属性值就可能引起原型对象的属性值发生变化。

对于1和2,例如:                                                        对于3,例如:

   

 

补充:动态原型模式、寄生构造函数模式、稳妥构造函数模式

动态原型模式:相比原型模式多了个动态,为啥叫动态呢,只是构造函数中加入了判断语句,用于判断属性或方法是否存在。

比如:

问题:上面通过定义p变量来构造的对象可以正常输出,但利用全局对象,通过window输出,其他属性没有问题,而显示方法为undefined,并且浏览器输出为not a function。

解决:作为小白并不知道如何找相关的资料,但根据之前的学习,发现单纯通过构造函数模式不用原型模式,window对象是可以访问到方法的,所以,个人暂时认为,无法通过window对象访问到对象的原型对象。

实验:

可以看到,重新给Person的原型对象定义了一个grade属性并赋值,发现p对象可以正常访问到,而window却不能

这部分内容等看到window再回来补充吧

另外两个模式参考这个链接:https://www.jianshu.com/p/35664ff98a56

大部分和红宝书的内容相似,并且其中提到了new的机制可以看看。

new的过程:当解析器碰到new时,会创建一个新对象;把this赋值给这个新对象;执行构造函数中的代码;返回新对象。

 

对象就到这个吧,一个博客写太多估计也看不下去。上次提交是3月12号。中间天天给老板查资料写文档都快搞出焦虑症了,距离上次块一星期了,唉(长叹息以掩涕兮)

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值