2017-02-04 2 views

ответ

5

Мое предложение привыкают использовать неизменные операции, так что вы не изменить внутреннее состояние объекта.

Как указано в react docs:

Никогда не мутировать this.state непосредственно, как вызов SetState() впоследствии может заменить мутацию вы сделали. Относитесь к этому. Как будто это было неизменяемым.

В этом случае, вы можете [1] использование slice() получить новую копию массива, [2] манипулировать копию, и, затем, [3] SetState с новым массивом. Это хорошая оценка.

Нечто подобное:

let newIds = this.state.ids.slice() //copy the array 
newIds[1] = 'B' //execute the manipulations 
this.setState({ids: newIds}) //set the new state 
+0

Я думаю, что смысл этой строки заключается в следующем: 'this.state.a = 'a'', не меняет значения переменной состояния напрямую. ** обрабатывать this.state, как если бы он был неизменным **, всегда используйте 'setState' для изменения значений состояния. исправьте меня, если я ошибаюсь ?? –

+0

Массивы - это объекты в JS, поэтому они передаются * * reference * * (без проблем, если вы устанавливаете ключ состояния с новой строкой). Но изменение одного и того же массива/объекта из 'this.state' изменит один и тот же внутренний объект. – mrlew

+0

ohh, получил смысл спасибо :) –

3

Случай 1: Если вы знаете индекс, то вы можете написать это:

let ids = [...this.state.ids];  // create the copy of state array 
ids[index] = 'k';     //new value 
this.setState({ ids });   //update the value 

Случай 2: Если вы не знаете индекс, то первым использовать array.findIndex или любой другой цикл чтобы получить индекс элемента, который вы хотите обновить, после этого обновите значение и используйте setState.

Как это:

let ids = [...this.state.ids]; 
let index = ids.findIndex(el => /* condition */); 
ids[index] = 'k';     
this.setState({ ids });    
0

Опираясь на то, что @ Mayank-Шукла писал (случай 2: зная индекс элемента замены), это также может быть написана с Array.splice:

const replacement = 'B'; 
let copy = [...this.state.ids] 
copy = copy.splice(index, 1, replacement) 

this.setState({ 
    ids: copy, 
}) 

REPL Example

Две вещи отметить здесь:

  1. Array.splice- mutative; Он изменит массив, на котором он работает, но это мелкая копия массива из-за оператора распространения. Подробнее об этом ниже.
  2. Вы не можете напрямую назначить результат сращивания, так как возвращаемое значение Array.splice фактически является удаленными элементами. AKA: Не назначайте результат вашего среза переменной, которую вы собираетесь назначать идентификаторам в setState, или вы получите только удаленные значения.

Чтобы следить за неглубокие против глубоких копий из пункта 1, обратите внимание, что при замене ссылок на объекты (против строковых литералов в вопросе), вам нужно будет использовать что-то вроде lodash's cloneDeep.

Есть, однако, handful of other ways around this.

Вы также можете узнать больше о мелководье и глубине на SO itself.

Смежные вопросы