Это правда, что я написал много статей о Прокси, так что сегодня я не буду восполнять количество слов, давайте поджарим два каштана.
1. Виртуальные атрибуты
const person = {
name: 'xiaoyun',
province: '江苏省',
city: '南京市'
}
Для вышеперечисленных объектов нам может понадобиться адресная информация (сращенная по провинциям и городам), а перед этим мы можем воспользоваться следующими методами:
- Объявите свойство адреса непосредственно в объекте человека;
- Когда используется адресная информация, она склеивается по лицам.
Основным недостатком первого метода является то, что он загрязняет исходный объект, а второй метод очень негибкий. Теперь мы можем добиться лучших результатов через прокси:
const enhancePerson = new Proxy(person, {
get (target, name) {
switch (name) {
case 'address':
return `${target['province']}-${target['city']}`
default:
return target[name]
}
}
})
enhancePerson.address // 江苏省-南京市
Таким образом, мы можем реализовать виртуальное свойство, потому что оно не будет пройдено:
Object.keys(enhancePerson) // [ 'name', 'province', 'city' ]
Вот еще один момент, который, я думаю, легче игнорировать:
person === enhancePerson // false
enhancePerson.city = '苏州市'
enhancePerson.city === person.city // true
Очевидно, что эти два объекта не являются одним и тем же объектом, но я затронул свойство города человека, изменив свойство города в расширении человека, что мы обычно игнорируем.Если вы не установите метод set прокси, он сохранит значение по умолчанию. поведение:
set (target, propKey, value) {
target[propKey] = value
}
Может быть, некоторые студенты подумают, что это не для того, чтобы выпустить его наружу? Проверьте этот трюк:
const person = {
name: 'xiaoyun',
province: '江苏省',
city: '南京市',
get address () {
return `${this.province}-${this.city}`
}
}
const enhancePerson = new Proxy(person, {
ownKeys (target) {
return Object.keys(target).filter(item => item !== 'address')
}
})
enhancePerson.address // 江苏省-南京市
Object.keys(enhancePerson) // [ 'name', 'province', 'city' ]
Хотя вышеперечисленные функции реализованы, методов для перехвата ownKeys в Proxy слишком много, поэтому после того, как мы перехватим ownKeys, некоторые методы будут недоступны, а к результатам, возвращаемым перехватом ownKeys, также предъявляются строгие требования:
- Возвращаемый результат должен быть массивом
- И элементы массива должны быть типа String или Symbol
- Результат должен содержать все ненастраиваемые собственные свойства объекта.
- Если объект не может быть расширен, результат может содержать только свойства, которыми он владеет, и никакие другие свойства.
Поэтому обратите внимание на множество методов перехвата, иначе легко возникнут проблемы.
Совет: Свойство дескриптора свойства, не определенного в defineProperty, по умолчанию имеет значение true, в противном случае — значение false.
2. Разверните базовую операцию
Когда я впервые столкнулся с Python, меня больше впечатлила грамматика его List: arr[1:3], Раньше я только завидовал, но теперь я могу сделать его сам:
const arr = [1, 2, 3, 4, 5, 6, 7, 8]
const list = new Proxy(arr, {
get (target, name) {
if (name.includes(':')) {
const indexs = name.split(':')
return target.slice(indexs[0], indexs[1])
}
return target[name]
}
})
list['2:6'] // [ 3, 4, 5, 6 ]
Не правда ли 😎, для объектов мы тоже можем использовать аналогичный метод:
const obj = {
a: {
b: {
c: 'xiaoyun'
}
}
}
const obj1 = new Proxy(obj, {
get (target, name) {
const keys = name.split('.')
return keys.reduce((pre, next) => {
if (pre !== null && pre !== undefined) {
pre = pre[next]
}
return pre
}, target)
}
})
obj1['a.b.c'] // xiaoyun
Друзья, которым понравилась эта статья, прошу обратить внимание на мой номер подпискилюблю набирать код, узнать больше.