1

I am having trouble understanding why my component state does not change inside the for-loop.

Here's an example:

class Example extends React.Component {
    constructor() {
        super()
        this.state = { 
            labelCounter: 1, 
        }
    }


    componentDidMount() {                   
        for (let i = 0; i < 10; i++) {
            this.setState({ labelCounter: this.state.labelCounter + 1 })

            console.log(this.state.labelCounter) // this.statelabelCounter = 1
        }
    }

}

Whereas if I changed the code slightly to this, it seems to be changing as expected:

class Example extends React.Component {
    constructor() {
        super()
        this.state = { 
            labelCounter: 1, 
        }
    }


    componentDidMount() {                   
        for (let i = 0; i < 10; i++) {
            this.setState({ labelCounter: ++this.state.labelCounter })

            console.log(this.state.labelCounter)
        }
    }

}
Alejandro
  • 2,266
  • 6
  • 35
  • 63

2 Answers2

1

I think the issue you're having is that react batches updates to the state. This means that instead of it working synchronously, it just applies setState({ labelCounter: this.state.labelCounter + 1}) after the loop, and this.state.labelCounter + 1 is resolved to a fixed number (1 in this case), that is reapplied 10 times. So the labelCounter is set to 1 10 times.

In the last example you are updating by changing the property yourself (and not having react do it), which is why it works.

I would guess the best way to do it is to wait for a batch to have been applied (for example with setTimeout(x, 0)) and doing the rest after that, or trying to avoid this altogether.

SanderRonde
  • 301
  • 1
  • 10
  • 1
    You can also use a callback to get the value when it finishes updating as per the docs: https://facebook.github.io/react/docs/react-component.html#setstate – ren.rocks May 04 '17 at 18:35
0

Correct me if I am wrong, but "this.state.labelCounter + 1" is not the same as "this.state.labelCounter ++" because it is evaluating the state value before making the changes to the state value.

Another option would be "this.state.labelCounter += 1"

Source: (Not exactly similar) Difference between ++ and +=1 in javascript

Community
  • 1
  • 1