React类组件用Context遇map()非函数及方法调用错误求助
React Class组件Context使用中的错误原因解析
问题背景
在React Class组件中通过Context实现商品数量递增功能时,遇到两个问题:
- Products组件出现
map() is not a function错误 - 无法调用Context中的方法,抛出“is not a function”错误
相关代码片段
主组件state定义
state = [ {prodoctName : "food" , count : 0, id:0}, {prodoctName : "water" , count : 0, id:1}, {prodoctName : "store" , count : 0, id:2}, {prodoctName : "game" , count : 0, id:3}, {prodoctName : "how" , count : 0, id:4} ];
主组件Context Provider代码
increase = (id = 0)=>{ let newState = [...this.state]; newState[id].count += 1; this.setState(newState); } render() { return ( <> <MyContext.Provider value={{ increase : this.increase, reduce : this.reduce, sumCount : this.sumCount, state : this.state, }}> <Products></Products> </MyContext.Provider> </> ); }
Products组件代码
class Products extends Component { static contextType = MyContext; render() { return ( <> {this.context.state.map((p)=>{ return <Product key={p.id} ProductId={p.id}></Product> })} </> ); } }
Product组件代码
class Product extends Component{ static contextType = MyContext; render() { return ( <div> <span>{this.context.state[this.props.ProductId].prodoctName}</span> <span> {this.context.state[this.props.ProductId].count} </span> <button onClick={()=>{this.context.increase(this.props.ProductId)}}>+</button> </div> ); } }
错误原因分析
1. map() is not a function 错误
- React Class组件的state必须是对象类型,你直接将数组赋值给了state。当调用
setState时,React会把传入的新数组作为对象的属性合并(而非直接替换),导致后续this.state不再是数组,而是包含原数组元素的对象,自然无法调用数组的map方法。 - 修复方案:将数组嵌套在state的一个属性中,比如:
// 主组件state修改为对象结构 state = { products: [ {prodoctName : "food" , count : 0, id:0}, {prodoctName : "water" , count : 0, id:1}, {prodoctName : "store" , count : 0, id:2}, {prodoctName : "game" , count : 0, id:3}, {prodoctName : "how" , count : 0, id:4} ] }; // 对应修改increase方法 increase = (id = 0)=>{ // 复制products数组并修改对应项(避免直接修改原数据) let newProducts = [...this.state.products]; newProducts[id] = {...newProducts[id], count: newProducts[id].count + 1}; this.setState({ products: newProducts }); } // Context Provider的value调整 <MyContext.Provider value={{ increase : this.increase, // 若未实现reduce和sumCount,暂时移除或补充定义 state : this.state.products, }}>
2. “is not a function” 错误
- 你在Context的value中传入了
reduce和sumCount方法,但主组件中并未定义这两个方法,当子组件尝试调用它们时就会抛出“is not a function”错误。 - 修复方案:要么在主组件中补充实现
reduce和sumCount方法,要么从Context的value中移除这两个未定义的属性。
内容的提问来源于stack exchange,提问作者ArshiaCode
相关产品推荐
相关产品推荐

