React에서 setState를 사용하여 개체 업데이트
을 브브트 object object로 갱신할 수 ?setState
예를 들어 다음과 같습니다.
this.state = {
jasper: { name: 'jasper', age: 28 },
}
시도했습니다.
this.setState({jasper.name: 'someOtherName'});
또, 이하와 같이 됩니다.
this.setState({jasper: {name: 'someothername'}})
첫 번째 경우 구문 오류가 발생하고 두 번째 경우 구문 오류가 발생하지 않습니다.좋은 생각 있어요?
여기에는 여러 가지 방법이 있습니다.상태 갱신은 비동기 조작이기 때문에 상태 오브젝트를 갱신하기 위해서는 다음과 같이 업데이터 기능을 사용해야 합니다.setState
.
1 - 가장 심플한 것:
''을 보세요.jasper
하다
this.setState(prevState => {
let jasper = Object.assign({}, prevState.jasper); // creating copy of state variable jasper
jasper.name = 'someothername'; // update the name property, assign a new value
return { jasper }; // return new object jasper object
})
「 」를 하는 대신에, 「 」를 사용합니다.Object.assign
을 사용하다
let jasper = { ...prevState.jasper };
this.setState(prevState => ({
jasper: { // object that we want to update
...prevState.jasper, // keep all other key-value pairs
name: 'something' // update the value of specific key
}
}))
Object.assign
★★★★★★★★★★★★★★★★★」Spread Operator
에서는 얕은 복사만 작성되므로 중첩된 개체 또는 개체 배열을 정의한 경우에는 다른 접근법이 필요합니다.
중첩된 상태 개체를 업데이트하는 중:
상태를 다음과 같이 정의했다고 가정합니다.
this.state = {
food: {
sandwich: {
capsicum: true,
crackers: true,
mayonnaise: true
},
pizza: {
jalapeno: true,
extraCheese: false
}
}
}
추가 치즈 오브 피자 개체를 업데이트하려면:
this.setState(prevState => ({
food: {
...prevState.food, // copy all other key-value pairs of food object
pizza: { // specific object of food object
...prevState.food.pizza, // copy all pizza key-value pairs
extraCheese: true // update value of specific key
}
}
}))
개체 배열 업데이트 중:
ToDo 앱이 있고 다음 형식으로 데이터를 관리하고 있다고 가정합니다.
this.state = {
todoItems: [
{
name: 'Learn React Basics',
status: 'pending'
}, {
name: 'Check Codebase',
status: 'pending'
}
]
}
객체의 ToDo 객체의 합니다.condition=true
갱신된 값을 사용하여 새 개체를 반환합니다.그렇지 않으면 동일한 개체를 반환합니다.
let key = 2;
this.setState(prevState => ({
todoItems: prevState.todoItems.map(
el => el.key === key? { ...el, status: 'done' }: el
)
}))
제안:개체에 고유한 값이 없으면 배열 인덱스를 사용합니다.
이것이 가장 빠르고 읽기 쉬운 방법입니다.
this.setState({...this.state.jasper, name: 'someothername'});
this.state.jasper
새, 이름 등이 이미 되어 있습니다.name: 'someothername'
사용할 수 있습니다.
여기서 분산 연산자와 일부 ES6 사용
this.setState({
jasper: {
...this.state.jasper,
name: 'something'
}
})
여기에 많은 답변이 있는 것은 알지만, 그 중 어느 것도 setState 이외의 새로운 오브젝트의 복사본을 작성하지 않고 단순히 setState({newObject})를 작성하지 않는 것이 놀랍습니다.깔끔하고 간결하며 신뢰성이 뛰어납니다.이 경우:
const jasper = { ...this.state.jasper, name: 'someothername' }
this.setState(() => ({ jasper }))
또는 동적 속성(양식에 매우 유용함)의 경우
const jasper = { ...this.state.jasper, [VarRepresentingPropertyName]: 'new value' }
this.setState(() => ({ jasper }))
후크를 사용하여 다음과 같이 할 수 있습니다.
const [student, setStudent] = React.useState({name: 'jasper', age: 28});
setStudent((prevState) => ({
...prevState,
name: 'newName',
}));
나는 이 용액을 사용했다.
다음과 같은 중첩 상태가 있는 경우:
this.state = {
formInputs:{
friendName:{
value:'',
isValid:false,
errorMsg:''
},
friendEmail:{
value:'',
isValid:false,
errorMsg:''
}
}
}
현재 상태를 복사하고 변경된 값으로 다시 할당하는 handleChange 함수를 선언할 수 있습니다.
handleChange(el) {
let inputName = el.target.name;
let inputValue = el.target.value;
let statusCopy = Object.assign({}, this.state);
statusCopy.formInputs[inputName].value = inputValue;
this.setState(statusCopy);
}
이벤트 리스너와 함께 html을 만듭니다.상태 개체와 동일한 이름을 사용하십시오(이 경우 'friendName').
<input type="text" onChange={this.handleChange} " name="friendName" />
이거 해봐, 잘 될 거야
this.setState(Object.assign(this.state.jasper,{name:'someOtherName'}));
상태 개체를 만듭니다.
this.state = {
objName: {
propertyOne: "",
propertyTwo: ""
}
};
를 사용하여 합니다.setState
this.setState(prevState => ({
objName: {
...prevState.objName,
propertyOne: "Updated Value",
propertyTwo: "Updated value"
}
}));
이것은 immer immutabe 유틸리티를 사용하는 또 다른 솔루션이며, 쉽게 네스트된 오브젝트에 매우 적합하며, 돌연변이는 신경 쓰지 말아야 합니다.
this.setState(
produce(draft => {
draft.jasper.name = 'someothername'
})
)
기능 컴포넌트의 후크 사용:
const [state, setState] = useState({jasper: { name: 'jasper', age: 28 }})
const nameChangeHandler = () => {
setState(prevState => ({
...prevState,
prevState.jasper.name = "Anurag",
prevState.jasper.age = 28
})
)
}
이 경우 콜백 기반의 접근방식을 사용하여 상태를 갱신할 것을 권장합니다.이 접근방식을 사용하면 이전 상태가 완전히 갱신되고 이전에 갱신된 상태에 따라 갱신됩니다.
첫 번째 경우는 구문 오류입니다.
나머지 컴포넌트를 볼 수 없기 때문에 이 상태에서는 오브젝트를 네스트 하는 이유를 알 수 없습니다.오브젝트를 컴포넌트 상태로 중첩하는 것은 좋지 않습니다.초기 상태를 다음과 같이 설정하십시오.
this.state = {
name: 'jasper',
age: 28
}
이렇게 하면 이름을 갱신할 수 있습니다.
this.setState({
name: 'Sean'
});
그것이 당신이 목표로 하는 것을 달성할 수 있습니까?
더 크고 복잡한 데이터 저장소에는 Redux와 같은 것을 사용합니다.하지만 그것은 훨씬 더 발전된 것이다.
컴포넌트 상태의 일반적인 규칙은 컴포넌트의 UI 상태(액티브, 타이머 등)를 관리하기 위해서만 사용합니다.
다음 참고 자료를 확인하십시오.
- https://facebook.github.io/react/docs/react-component.html#state
- https://facebook.github.io/react/docs/state-and-lifecycle.html
키가 문자열인 개체를 업데이트하는 경우
예: 상태 객체가 다음과 같습니다.
serviceDays: {
Sunday: true,
Monday: true,
Tuesday: false,
Wednesday: true,
Thurday: false,
Friday: true,
Saturday: true
}
따라서 다음과 같은 방법으로 업데이트 할 수 있습니다.
const onDayClick = day => {
const { serviceDays } = this.state
this.setState(prevState => ({
serviceDays: {
...prevState.serviceDays,
[day]: serviceDays[day] ? false : true
}
}))
}
다른 옵션은 Jasper 개체에서 변수를 정의하고 변수를 호출하는 것입니다.
확산 연산자: ES6
this.state = { jasper: { name: 'jasper', age: 28 } }
let foo = "something that needs to be saved into state"
this.setState(prevState => ({
jasper: {
...jasper.entity,
foo
}
})
다음과 같이 시험해 볼 수 있습니다.
this.setState(prevState => {
prevState = JSON.parse(JSON.stringify(this.state.jasper));
prevState.name = 'someOtherName';
return {jasper: prevState}
})
또는 기타 속성의 경우:
this.setState(prevState => {
prevState = JSON.parse(JSON.stringify(this.state.jasper));
prevState.age = 'someOtherAge';
return {jasper: prevState}
})
또는 handleChage 함수를 사용할 수 있습니다.
handleChage(event) {
const {name, value} = event.target;
this.setState(prevState => {
prevState = JSON.parse(JSON.stringify(this.state.jasper));
prevState[name] = value;
return {jasper: prevState}
})
}
및 HTML 코드:
<input
type={"text"}
name={"name"}
value={this.state.jasper.name}
onChange={this.handleChange}
/>
<br/>
<input
type={"text"}
name={"age"}
value={this.state.jasper.age}
onChange={this.handleChange}
/>
다음과 같이 시도해 볼 수 있습니다. (주의: 입력 태그 이름 === 객체의 필드)
<input name="myField" type="text"
value={this.state.myObject.myField}
onChange={this.handleChangeInpForm}>
</input>
-----------------------------------------------------------
handleChangeInpForm = (e) => {
let newObject = this.state.myObject;
newObject[e.target.name] = e.target.value;
this.setState({
myObject: newObject
})
}
심플하고 역동적인 방법
이렇게 하면 작업이 완료되지만, 모든 ID를 부모에게 설정해야 합니다. 그러면 부모가 개체 이름(id = "display")을 가리키고 개체 재스퍼 내부의 입력 요소 = 속성의 이름을 지정해야 합니다.
handleChangeObj = ({target: { id , name , value}}) => this.setState({ [id]: { ...this.state[id] , [name]: value } });
비동기 사용 안 함 및 대기 이 사용...
funCall(){
this.setState({...this.state.jasper, name: 'someothername'});
}
Async And Wait와 함께 사용하는 경우 이 옵션을 사용합니다.
async funCall(){
await this.setState({...this.state.jasper, name: 'someothername'});
}
또한 Alberto Piras 솔루션에 따라 모든 "state" 객체를 복사하지 않을 경우 다음 절차를 수행합니다.
handleChange(el) {
let inputName = el.target.name;
let inputValue = el.target.value;
let jasperCopy = Object.assign({}, this.state.jasper);
jasperCopy[inputName].name = inputValue;
this.setState({jasper: jasperCopy});
}
다음을 사용해 보십시오.
const { jasper } = this.state; //Gets the object from state
jasper.name = 'A new name'; //do whatever you want with the object
this.setState({jasper}); //Replace the object in state
input html input name attribute를 사용하면 오브젝트 속성을 갱신하기 위해 보다 역동적인 접근을 할 수 있습니다.
<input type="text" name="fname" handleChange={(e: any) => { updatePerson(e) }}/>
<input type="text" name="lname" handleChange={(e: any) => { updatePerson(e) }}/>
리액트 / TSX object.displaces
const [person, setPerson] = useState<IPerson>({});
function updatePerson(e: React.ChangeEvent<HTMLInputElement>): void {
const { name, value } = e.currentTarget;
setPerson(prevState => {
const newState = Object.assign(person, { [name]: value })
return { ...prevState, ...newState };
});
}
FC의 예:
const [formData, setformData] = useState({
project_admin_permissions: {
task_forms: false,
auto_assign_rules: false,
project_notes: true,
alerts: false,
update_criteria: true,
project_flow: false,
reports: false,
}
})
const handleChangeCheckBox = (e) => {
setformData({
...formData, project_admin_permissions: { ...formData.project_admin_permissions, [e.target.name]: e.target.checked }
})
}
이 설정은 나에게 유효했다.
let newState = this.state.jasper;
newState.name = 'someOtherName';
this.setState({newState: newState});
console.log(this.state.jasper.name); //someOtherName
두 번째 접근법이 작동하지 않는 이유는{name: 'someothername'}
동등.{name: 'someothername', age: undefined}
그 때문에,undefined
원래 나이 값을 덮어씁니다.
네스트된 객체의 상태를 변경하는 경우 Unfound.js를 사용하는 것이 좋습니다.
this.state = {
jasper: Record({name: 'jasper', age: 28})
}
const {jasper} = this.state
this.setState({jasper: jasper.set(name, 'someothername')})
언급URL : https://stackoverflow.com/questions/43638938/updating-an-object-with-setstate-in-react
'programing' 카테고리의 다른 글
util 스키마를 사용하여 목록을 자동 배선하면 NoSchBeanDefinition이 제공됩니다.예외. (0) | 2023.03.07 |
---|---|
ASP 입수 방법크롬을 사용하여 XML 대신 JSON을 반환하는 NET Web API를 선택하십시오. (0) | 2023.03.07 |
Angular에서 ng-show를 전환하려면 어떻게 해야 합니까?부울에 기반한 JS? (0) | 2023.03.07 |
ACF 리피터 출력의 총 행 수를 카운트하는 방법 (0) | 2023.03.02 |
1면에 올빼미 회전목마 추가하는 방법 (0) | 2023.03.02 |