js

JS高级知识总结03

严格模式,原型/原型链,继承,ES6类新特性

Posted by AzirKxs on 2022-11-10
Estimated Reading Time 6 Minutes
Words 1.5k In Total
Viewed Times

js高级知识总结03

Proxy

在vue2中,我们使用Object.defineProperty方法来监听数据的变化

vue2监听原理

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
const obj = {
name:'kxs',
age: 22,
height:175
}

const keys = Object.keys(obj);

for(const key of keys){
let value = obj[key]
Object.defineProperty(obj,key,{
set: function(newValue){
console.log(`监听到了变化,给${key}设置了新的值:${newValue}`)
value = newValue
},
get: function(){
return value
}
})
}

obj.name = 'azir' //监听到了变化,给name设置了新的值:azir

Object.defineProperty的弊端

  1. Object.defineProperty的设计初衷并不是用来监听数据变化的
  2. 只能监听到设置和获取,无法监听增加属性,删除属性等更丰富的操作

Proxy监听

proxy的设计就是专门用来监听数据变化的,proxy意为代理,,如果我们希望监听一个对象的相关操作,那么可以先创建一个代理对象,之后通过代理对象来完成对原本的对象进行的操作,代理对象可以监听我们想要对原对象进行那些操作

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
const obj = {
name:'kxs',
age: 22,
height:175
}

//1.创建一个proxy对象
const objProxy = new Proxy(obj,{
//捕获器
})

//2.对obj的所有操作,应该去找objProxy
console.log(objProxy.name) //kxs
objProxy.name = 'azir'
console.log(objProxy.name) //azir

捕获器

Proxy构造函数的第二个参数为捕获器

捕获器的所有方法

image-20221029192145952

监听set和get

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
const obj = {
name:'kxs',
age: 22,
height:175
}

//1.创建一个proxy对象
const objProxy = new Proxy(obj,{
//捕获器
get: function(target,key) {
console.log(`监听到了${key}的获取`)
return target[key]
},
set: function(target,key,value){
console.log(`监听到了${key}的变化`)
target[key] = value
}
})

//2.对obj的所有操作,应该去找objProxy
console.log(objProxy.name) //监听到了name的获取 kxs

Reflect

Reflect 是什么?

  • Reflect 是一个内置的 JS 对象,它提供了一系列方法,可以让开发者通过调用这些方法,访问一些 JS 底层功能。由于它类似于其他语言的反射,因此取名为 Reflect。

它可以做什么?

  • 使用 Reflect 可以实现诸如:属性的赋值与取值、调用普通函数、调用构造函数、判断属性是否存在与对象中 等等功能。

这些功能不是已经存在了吗?为什么还需要用 Reflect 实现一次?

  • 有一个重要的理念,在 ES5 就被提出:减少魔法、让代码更加纯粹(语言的方法使用 API 实现,而不使用特殊语法实现),这种理念很大程度上是受到函数式编程的影响。
  • ES6 进一步贯彻了这种理念,它认为,对属性内存的控制、原型链的修改、函数的调用等等,这些都属于底层实现,属于一种魔法,因此,需要将它们提取出来,形成一个正常的 API,并高度聚合到某个对象中,于是就造就了 Reflect 对象。
  • 因此,你可以看到 Reflect 对象中有很多的 API 都可以使用过去的某种语法或其他 API 实现。

reflect的部分API

Reflect API 用处 等同于
Reflect.get(target, propertyKey) 读取对象 target 的属性 propertyKey 对象的属性值读取操作
Reflect.set(target, propertyKey, value) 设置对象 target 的属性 propertyKey 的值为 value 对象的属性赋值操作
Reflect.has(target, propertyKey) 判断一个对象是否拥有一个属性 in 操作符
Reflect.defineProperty(target, propertyKey, attributes) 类似于 Object.defineProperty,不同的是如果配置出现问题,返回 false 而不是报错 Object.defineProperty
Reflect.deleteProperty(target, propertyKey) 删除一个对象的属性 delete 操作符
Reflect.apply(target, thisArgument, argumentsList) 调用一个指定的函数,并绑定 this 和参数列表 函数调用操作
Reflect.construct(target, argumentsList) 用构造函数的方式创建一个对象 new 操作符

Reflect和Proxy共同完成代理

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
const obj = {
_age: 22,
_height:175,
_name:'kxs',
set name(newValue){
this._name = newValue //此时的this指向objProxy
}
}

const objProxy = new Proxy(obj,{
set: function(target,key,value,receiver){
const isSuccess = Reflect.set(target,key,value,receiver)
if(!isSuccess){
throw new Error(`set${key} failure`)
}
console.log(`监听到了${key}更改为了${value}`)
}


})

objProxy.name = 'azir' //打印两次,监听到了两次变化

1.使用reflect反射,不直接操作原对象

2.Reflect .set有返回boolean值,可以判断此次操作是否成功

3.Reflect.set/get最后一个参数,可以决定对象访问其setter/getter的this指向

Reflect.construct

1
2
Reflect.construct(super,[参数],target)
//创建target对象时执行super构造函数中的代码

Promise

promise是js中进行异步编程的解决方案,指定回调函数的方式更加灵活,支持链式调用,可以解决回调地狱的问题

Promise被分为了三种状态:pending(进行中),fulfilled(已成功),rejected(已失败)

Pomise状态更改的方式:

  • resolve(value): 如果当前是 pending 就会变为 resolved
  • reject(error): 如果当前是 pending 就会变为 rejected
  • 抛出异常: 如果当前是 pending 就会变为 rejected

promise执行的基本流程

1.使用promise包裹一个异步操作,执行异步操作

2.如果成功,执行resolve()函数,promise的状态被改为resolved,执行调用then()中的第一个回调函数,返回一个新的promise对象

3.如失败,执行reject()函数,promise的状态被改为rejected,执行调用then()中的第二个回调函数,返回一个新的promise对象

image-20221030105331028

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
//使用setTimeout来模拟一个请求数据的过程
let promise = new Promise((resolve,reject)=>{
setTimeout(()=>{
let id = '2019006152'
console.log('请求了一个用户的ID')
resolve(id)
},2000)
})
promise.then(res=>{
return new Promise((resolve,reject)=>{
setTimeout(()=>{
let name = 'azir'
console.log('根据id请求了一个name')
resolve(name)
},2000)})
}).then(res=>{
console.log('查询到的name为:'+res)
}).catch(err=>{
console.log('发生了错误')
})

实例方法

resolve

reject

catch

finally

类方法

Promise.resolve()

Promise.reject()

Promise.race()

Promise.all()

Promise.any()

Promise.allSettled()


如果这篇文章对你有帮助,可以bilibili关注一波 ~ !此外,如果你觉得本人的文章侵犯了你的著作权,请联系我删除~谢谢!