Я использую параметр rest для выполнения некоторых операций, но в результате некоторые свойства исчезли.
Формат данных this.props выглядит так:
```
this.props = {
data: [{...}, ...],
...
}
```
И я попытался успокоить его так:
```
let {showWaveAnimation, ...otherProps} = this.props;
console.info('data' in otherProps); // false
console.info('data' in this.props); //true
```
Почему свойство data потеряно после того, как я попробовал операцию отдыха?
По MDN нашел описание:
rest parameters are only the ones that haven't been given a separate name (i.e. formally defined in function expression), while the arguments object contains all arguments passed to the function;
Что здесь означает separate name? Означает ли это, что свойства, которые простираются от его прототипа, не останутся без покоя? Но после того, как я попробовал следующие утверждения, я получил тот же результат, я сбиваю с толку.
```
class Parent {
constructor() {
this.props = {
data: '123',
};
}
}
class Child extends Parent {
constructor() {
super();
this.props.childProp = 'test';
let {test, ...otherProps} = this.props;
console.info('data' in this.props, 'data' in otherProps);
// true true
}
}
new Child();
```
Неправильное поведение прежнего кода после транспиляции Babel, может быть проблема с плагином Babel?
ДОБАВИТЬ: Я обнаружил, что эта концепция может быть более точной при описании моих операций с rest. https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Destructuring_assignment#Rest_in_Object_Destructuring
Не хочу быть педантичным, но, похоже, вы действительно спрашиваете о оператор распространения. Он использует тот же синтаксис, но имеет тонкую, но ключевую разницу в использовании.
@DrewReese Я думаю, что действительно ищу правильный метод отдыха при деструктуризации объекта?



![Безумие обратных вызовов в javascript [JS]](https://i.imgur.com/WsjO6zJb.png)


Параметр rest позволяет получить все остальные атрибуты, еще не выбранные по идентификатору, предшествующему ему в назначении.
const obj = {
a: 1,
b: 2,
c: 3
}
const { a, ...rest } = obj;
console.info(a);
console.info(rest);Вышеупомянутый obj имеет свойство с именем a, поэтому он деструктурируется из obj и назначается переменной a, затем все остальные свойства назначаются в объекте для rest.
const obj = {
a: 1,
b: 2,
c: 3
}
const { d, ...rest } = obj;
console.info(d);
console.info(rest);Здесь obj не имеет свойства с именем d. Таким образом, он деструктурируется из obj как undefined и присваивается переменной a. Затем a передаются все другие свойства, которые еще не присвоены, то есть b, c и rest.
В вашем коде otherProps имеет те же свойства, что и this.props, потому что объект this.props не имеет свойства с именем test. Другими словами, чтобы разрушить объект, вы должны знать его структуру.
Это не ответ на этот вопрос: console.info('data' in otherProps); // false
@Rajesh На самом деле это настройка enumerable, я добавляю пример в ответ.
rest parameters are only the ones that haven't been given a separate name (i.e. formally defined in function expression), while the arguments object contains all arguments passed to the function;
What does separate name here means? Is it means properties that extends from its prototype would not be rest? But after I tried the following statements, I got the same result, I am confusing.
Учитывая определение функции function foo(a, b, ...c) {}, аргументы a и b являются именованными параметрами, тогда как остальные переданные аргументы распространяются на последнюю переменную c. Теперь cявляется - именованная переменная, но любые параметры, переданные с третьей, будут доступны только в c, то есть c[0].
Теперь ваша ошибка console.info возникает из-за использования вами оператора in. Вы определили объект const foo = {'data': 'bar'}. 'data' in foo - истина, но 'blarg' in foo - ложь, поскольку foo не содержит ключа / свойства с именем 'blarg'.
Фактически вы используете оператор распространения, чтобы разложить свой объект props на несколько именованных переменных.
const object = {
data: 'foo',
other: 'bar',
moreData: [1,2,3],
};
// Example usage of the spread operator
const { data, ...allTheRest} = object; // data is destructured, other and moreData into allTheRest
console.info(data);
console.info(allTheRest);
// in operator
console.info('data' in object); // true
console.info('data' in allTheRest); // false
console.info('moreData' in allTheRest); // true// This is an example of the rest operator
const foo = (...allTheArgs) => {
allTheArgs.forEach(e => console.info(e));
}
foo(1,2,3); // all the args are collected into a single array variable in the functionconst bar = (a, b, ...c) => {
console.info(`a: ${a}`);
console.info(`b: ${b}`);
console.info(`c: ${c}`);
};
bar('this is first param', 42, 'foo', 'bar', '1', 2, 'stackoverflow');На самом деле я обнаружил, что свойство data в моем объекте не перечислимо, но спасибо за ответ! Что меня смущает, так это то, могу ли я назвать a, а b в вашем коде получил отдельное имя?
Я добавил третий пример, чтобы показать, как использовать a и b. Надеюсь, это ответит на ваш вопрос.
Я понял, почему в моем результате отдыха исчезли «данные», это свойство enumerable поля «данные»!
После того, как свойство установлено как enumerable: false, мы не можем получить его с помощью операции rest при деструктуризации объекта.
По данным MDN
The Rest/Spread Properties for ECMAScript proposal (stage 3) adds the rest syntax to destructuring. Rest properties collect the remaining own enumerable property keys that are not already picked off by the destructuring pattern.
Думаю, этот пример может более точно объяснить мои идеи:
const person = {
name: 'Dave',
surname: 'Bowman'
};
Object.defineProperty(person, 'age', {
enumerable: false, // Make the property non-enumerable
value: 25
});
console.info(person['age']); // => 25
const clone = {
...person
};
console.info(clone); // => { name: 'Dave', surname: 'Bowman' }Вы меняете / настраиваете enumerable: false для данных? Его не видно под вопросом
@Rajesh На самом деле, это именно false, но он определяется фреймворком, поэтому я не заметил этого вначале.
@Rajesh Привет, я использую его в
Object, поэтому нет необходимости хранить его в индексе как массив? И операция, которую я написал в классеChild, может нормально работать.