Удаление собственности в JavaScript
На этой странице представлено много разных опций не потому, что большинство опций неверны, или потому, что ответы дублируются, а потому, что подходящая техника зависит от ситуации, в которой вы находитесь, и целей задач, которые вы и / или ваша команда пытается выполнить. Чтобы ответить на ваш вопрос однозначно, нужно знать:
- Версия ECMAScript, на которую вы нацелены
- Диапазон типов объектов, для которых вы хотите удалить свойства, и тип имен свойств, которые необходимо пропустить (Только строки? Символы? Слабые ссылки, сопоставленные с произвольными объектами? Все это были типы указателей свойств в JavaScript годами)
- Этос / паттерны программирования, которые вы и ваша команда используете. Вы предпочитаете функциональные подходы, а мутация в вашей команде - это словесно, или вы используете методы объектно-ориентированных мутаций на Диком Западе?
- Хотите ли вы достичь этого на чистом JavaScript или хотите и можете использовать стороннюю библиотеку?
После того, как на эти четыре запроса получен ответ, в JavaScript есть четыре категории «удаления свойств», которые можно выбрать для достижения ваших целей. Это:
Мутативное удаление свойства объекта, небезопасно
Эта категория предназначена для работы с литералами объекта или экземплярами объекта, когда вы хотите сохранить / продолжить использовать исходную ссылку и не используете функциональные принципы без сохранения состояния в вашем коде. Пример синтаксиса в этой категории:
'use strict'
const iLikeMutatingStuffDontI = { myNameIs: 'KIDDDDD!', [Symbol.for('amICool')]: true }
delete iLikeMutatingStuffDontI[Symbol.for('amICool')] // true
Object.defineProperty({ myNameIs: 'KIDDDDD!', 'amICool', { value: true, configurable: false })
delete iLikeMutatingStuffDontI['amICool'] // throws
Эта категория является самой старой, наиболее простой и широко поддерживаемой категорией удаления имущества. Он поддерживает Symbol
& индексы массивов в дополнение к строкам и работает во всех версиях JavaScript, кроме самого первого выпуска. Тем не менее, это мутация, которая нарушает некоторые принципы программирования и влияет на производительность. Это также может привести к неперехваченным исключениям при использовании ненастраиваемых свойств в строгом режиме .
Пропуск свойства строки на основе покоя
Эта категория предназначена для работы с обычными объектами или массивами в более новых разновидностях ECMAScript, когда требуется немутативный подход и вам не нужно учитывать ключи символов:
const foo = { name: 'KIDDDDD!', [Symbol.for('isCool')]: true }
const { name, ...coolio } = foo // coolio doesn't have "name"
const { isCool, ...coolio2 } = foo // coolio2 has everything from `foo` because `isCool` doesn't account for Symbols :(
Мутативное удаление свойства объекта, безопасно
Эта категория предназначена для работы с литералами объекта или экземплярами объекта, когда вы хотите сохранить / продолжить использовать исходную ссылку, защищая от исключений, возникающих в неконфигурируемых свойствах:
'use strict'
const iLikeMutatingStuffDontI = { myNameIs: 'KIDDDDD!', [Symbol.for('amICool')]: true }
Reflect.deleteProperty(iLikeMutatingStuffDontI, Symbol.for('amICool')) // true
Object.defineProperty({ myNameIs: 'KIDDDDD!', 'amICool', { value: true, configurable: false })
Reflect.deleteProperty(iLikeMutatingStuffDontI, 'amICool') // false
Кроме того, хотя изменяющиеся объекты на месте не сохраняют состояние, вы можете использовать функциональную природу Reflect.deleteProperty
для частичного применения и других функциональных методов, которые невозможны с delete
операторами.
Пропуск свойства строки на основе синтаксиса
Эта категория предназначена для работы с обычными объектами или массивами в более новых разновидностях ECMAScript, когда требуется немутативный подход и вам не нужно учитывать ключи символов:
const foo = { name: 'KIDDDDD!', [Symbol.for('isCool')]: true }
const { name, ...coolio } = foo // coolio doesn't have "name"
const { isCool, ...coolio2 } = foo // coolio2 has everything from `foo` because `isCool` doesn't account for Symbols :(
Пропуск библиотечного имущества
Эта категория обычно обеспечивает большую функциональную гибкость, включая учет символов и пропуск более чем одного свойства в одном выражении:
const o = require("lodash.omit")
const foo = { [Symbol.for('a')]: 'abc', b: 'b', c: 'c' }
const bar = o(foo, 'a') // "'a' undefined"
const baz = o(foo, [ Symbol.for('a'), 'b' ]) // Symbol supported, more than one prop at a time, "Symbol.for('a') undefined"