如何立即为数组设置状态?

How to setState for array immediately?

我 运行 遇到了一个与更新 React 中的状态有关的问题。

嗯,我有一些数据,我想用这些数据构建一个 table。但是,我想先过滤它。过滤效果很好,但我只有在更新过滤后的数据并将其扔到下一个组件时遇到问题...(我知道 setState 不会立即工作...)

ReportTable组件中的updatedReports还没有过滤数据... 修复它和更新数组状态的最佳方法是什么。

export default class ReportContent extends React.Component {

constructor(props) {
    super(props);
    this.state = {
        currentReports: this.props.reports
    };
}

_filterBy(option) {
    let updatedReports = [...this.props.reports].filter(report => {
        if (report.organizations === option || report.reportType === option) {
            return report;
        }
    });
    console.log(updatedReports);
    this.setState({currentReports: updatedReports});
}

render() {
    return (
        <div className="reports-table">
            <ReportMenu organizations={this.props.organizations} reportTypes={this.props.reportTypes}
                        filterBy={this._filterBy.bind(this)}/>
            <ReportTable updatedReports={this.state.currentReports}/>
        </div>
    );
}

}

您也许可以使用组件生命周期方法。 Here is more info.

componentDidMount 应该可以解决问题。你可以这样做:

componentDidMount(){
    let updatedReports = [...this.props.reports].filter(report => {
        if (report.organizations === option || report.reportType === option) {
            return report;
        }
    });
    this.setState({currentReports: updatedReports});
}

或者在 componentDidMount 中调用你的方法 _filterBy

希望对您有所帮助。

您提供的代码没有问题。 setState 如果正确调用应该可以工作。我敢打赌,问题出在您的其他组件或数据中。

这是一个使用您的代码的片段。我不知道你是如何实现你的其他组件的,所以我只是在这里做了一些假设。

class ReportMenu extends React.Component {
    render() {
        return <div className="well well-default">
            <select className="form-control" onChange={(e) => {
                this.props.filterBy(e.target.value)
            }}>
                <option> - </option>
                {this.props.organizations.map(
                    (item, index) => <option key={index}>{item}</option>
                )}
            </select>
            <br/>
            <select className="form-control" onChange={(e) => {
                this.props.filterBy(e.target.value)
            }}>
                <option> - </option>
                {this.props.reportTypes.map(
                    (item, index) => <option key={index}>{item}</option>
                )}
            </select>
        </div>
    }
}

class ReportTable extends React.Component {
    render() {
        return <table className="table table-bordered">
            <tbody>
                {this.props.updatedReports.map(
                    (item, index) => <tr key={index}>
                        <td>{index}</td>
                        <td>{item.organizations}</td>
                        <td>{item.reportType}</td>
                    </tr>
                )}
            </tbody>
        </table>
    }
}

class ReportContent extends React.Component {
    constructor(props) {
        super(props);
        this.state = {
            currentReports: this.props.reports
        };
    }
    _filterBy(option) {
        let updatedReports = this.props.reports.filter(report => {
            if (report.organizations === option || report.reportType === option) {
                return report;
            }
        });
        console.log(updatedReports);
        this.setState({currentReports: updatedReports});
    }
    render() {
        return (
            <div className="reports-table">
                <ReportMenu 
                    organizations={this.props.organizations} 
                    reportTypes={this.props.reportTypes} 
                    filterBy={this._filterBy.bind(this)}/>
                <ReportTable updatedReports={this.state.currentReports}/>
            </div>
        );
    }
}

class App extends React.Component {
    render() {
        const reports = [
            {
                organizations: 'orgA',
                reportType: 'typeA'
            }, {
                organizations: 'orgA',
                reportType: 'typeB'
            }, {
                organizations: 'orgB',
                reportType: 'typeA'
            }, {
                organizations: 'orgB',
                reportType: 'typeB'
            }
        ];
        return <div className="container">
            <h1 className="page-header">Reports</h1>
            <ReportContent 
                reports={reports} 
                organizations={['orgA', 'orgB']} 
                reportTypes={['typeA', 'typeB']}/>
        </div>
    }
}

ReactDOM.render(<App/>, document.getElementById('root'));