setState 不适用于 Switch 块
setState not working with Switch block
我正在尝试构建一个小型聊天机器人,如果不是因为这个错误,我似乎已经接近完成。问题似乎是我的 switch 语句没有正确处理 setState。
Uquestion extends React.Component {
constructor(props) {
super(props);
this.state = {
text: this.props.text,
response: "Here is the answer"
}
this.handleChange = this.handleChange.bind(this)
this.key = this.key.bind(this)
this.fetchResponse = this.fetchResponse.bind(this)
}
handleChange(event) {
this.setState({
question: event.target.value
})
}
fetchResponse() {
switch(this.state.searchKey) {
case "BBQ":
this.setState({
response:"Texas BBQ"
})
break;
case "book":
this.setState({
response:"It's close, but probably The Night in Question by Tobias Wolff."
})
break;
case "restaurant":
this.setState({
response:"Andaman, a little Thai spot in Denton, Texas."
})
break;
case "work":
this.setState({
response:"Lots of this and lots of that."
})
break;
case "upbringing":
this.setState({
response:"Texas thunderstorms over endless plains."
})
break;
case "future":
this.setState({
response:"I hope to work on meaningful applications and write meaningful narratives"
})
break;
case "fun":
this.setState({
response:"When the moon is full, I write by candle light."
})
break;
default:
this.setState({
response:"Um, what?"
})
}
}
//this function sets a key that I will later use to fetch a response to the user's question.
key() {
var question=this.state.question;
var questionUpper=question.toUpperCase();
// the is not -1 determines if the phrase appears anywhere in the question.
if(questionUpper.search("FAVORITE FOOD")!==-1) {
this.setState({
searchKey:"BBQ"
}, this.fetchResponse())
}
else if(questionUpper.search("FAVORITE BOOK")!==-1) {
this.setState({
searchKey:"Book"
}, this.fetchResponse())
}
else if(questionUpper.search("FAVORITE RESTAURANT")!==-1) {
this.setState({
searchKey:"Restaurant"
},this.fetchResponse())
}
else if(questionUpper.search("WORK EXPERIENCE")!==-1) {
this.setState({
searchKey:"work"
},this.fetchResponse())
}
else if(questionUpper.search("GROWING UP")!==-1) {
this.setState({
searchKey:"upbringing"
},this.fetchResponse())
}
else if(questionUpper.search("FAVORITE AUTHOR")!==-1) {
this.setState({
searchKey:"author"
},this.fetchResponse())
}
else if(questionUpper.search("FUTURE")!==-1) {
this.setState({
searchKey:"future"
},this.fetchResponse())
}
else if (questionUpper.search("FOR FUN")!==-1) {
this.setState({
searchKey:"fun"
},this.fetchResponse())
}
else {
this.setState({
searchKey:"default"
}, this.fetchResponse())
}
}
render() {
return (
<div>
<p> {this.state.response} </p>
<textarea onChange = {this.handleChange} className="q"> {this.props.text} </textarea>
<button className="a" onClick={this.key}>Ask!</button>
</div>
);
}
}
ReactDOM.render(<Uquestion text="Type Question Here."/>, document.getElementById("content"))
您在 setState
函数中传递了错误的回调。在 fetchResponse
中,您写了一些错误的案例。我已经纠正了你的错误,你可以在 Codepen
中查看工作示例
错误:
this.setState({
searchKey: "book"
}, this.fetchResponse())
正确:
this.setState({
searchKey: "book"
}, this.fetchResponse)
你可以阅读 React 源代码
ReactComponent.prototype.setState = function (partialState, callback){
!(typeof partialState === 'object' || typeof partialState === 'function' || partialState == null) ? process.env.NODE_ENV !== 'production' ? invariant(false, 'setState(...): takes an object of state variables to update or a function which returns an object of state variables.') : _prodInvariant('85') : void 0;
this.updater.enqueueSetState(this, partialState);
if (callback) {
this.updater.enqueueCallback(this, callback, 'setState');
}
};
enqueueCallback: function (publicInstance, callback, callerName) {
ReactUpdateQueue.validateCallback(callback, callerName);
var internalInstance = getInternalInstanceReadyForUpdate(publicInstance);
if (!internalInstance) {
return null;
}
if (internalInstance._pendingCallbacks) {
internalInstance._pendingCallbacks.push(callback);
} else {
internalInstance._pendingCallbacks = [callback];
}
enqueueUpdate(internalInstance);
}
function enqueueUpdate(internalInstance) {
ReactUpdates.enqueueUpdate(internalInstance);
}
所以,我想你的回调是这样的:
this.setState({
searchKey:"BBQ"
}, this.fetchResponse)
我正在尝试构建一个小型聊天机器人,如果不是因为这个错误,我似乎已经接近完成。问题似乎是我的 switch 语句没有正确处理 setState。
Uquestion extends React.Component {
constructor(props) {
super(props);
this.state = {
text: this.props.text,
response: "Here is the answer"
}
this.handleChange = this.handleChange.bind(this)
this.key = this.key.bind(this)
this.fetchResponse = this.fetchResponse.bind(this)
}
handleChange(event) {
this.setState({
question: event.target.value
})
}
fetchResponse() {
switch(this.state.searchKey) {
case "BBQ":
this.setState({
response:"Texas BBQ"
})
break;
case "book":
this.setState({
response:"It's close, but probably The Night in Question by Tobias Wolff."
})
break;
case "restaurant":
this.setState({
response:"Andaman, a little Thai spot in Denton, Texas."
})
break;
case "work":
this.setState({
response:"Lots of this and lots of that."
})
break;
case "upbringing":
this.setState({
response:"Texas thunderstorms over endless plains."
})
break;
case "future":
this.setState({
response:"I hope to work on meaningful applications and write meaningful narratives"
})
break;
case "fun":
this.setState({
response:"When the moon is full, I write by candle light."
})
break;
default:
this.setState({
response:"Um, what?"
})
}
}
//this function sets a key that I will later use to fetch a response to the user's question.
key() {
var question=this.state.question;
var questionUpper=question.toUpperCase();
// the is not -1 determines if the phrase appears anywhere in the question.
if(questionUpper.search("FAVORITE FOOD")!==-1) {
this.setState({
searchKey:"BBQ"
}, this.fetchResponse())
}
else if(questionUpper.search("FAVORITE BOOK")!==-1) {
this.setState({
searchKey:"Book"
}, this.fetchResponse())
}
else if(questionUpper.search("FAVORITE RESTAURANT")!==-1) {
this.setState({
searchKey:"Restaurant"
},this.fetchResponse())
}
else if(questionUpper.search("WORK EXPERIENCE")!==-1) {
this.setState({
searchKey:"work"
},this.fetchResponse())
}
else if(questionUpper.search("GROWING UP")!==-1) {
this.setState({
searchKey:"upbringing"
},this.fetchResponse())
}
else if(questionUpper.search("FAVORITE AUTHOR")!==-1) {
this.setState({
searchKey:"author"
},this.fetchResponse())
}
else if(questionUpper.search("FUTURE")!==-1) {
this.setState({
searchKey:"future"
},this.fetchResponse())
}
else if (questionUpper.search("FOR FUN")!==-1) {
this.setState({
searchKey:"fun"
},this.fetchResponse())
}
else {
this.setState({
searchKey:"default"
}, this.fetchResponse())
}
}
render() {
return (
<div>
<p> {this.state.response} </p>
<textarea onChange = {this.handleChange} className="q"> {this.props.text} </textarea>
<button className="a" onClick={this.key}>Ask!</button>
</div>
);
}
}
ReactDOM.render(<Uquestion text="Type Question Here."/>, document.getElementById("content"))
您在 setState
函数中传递了错误的回调。在 fetchResponse
中,您写了一些错误的案例。我已经纠正了你的错误,你可以在 Codepen
错误:
this.setState({
searchKey: "book"
}, this.fetchResponse())
正确:
this.setState({
searchKey: "book"
}, this.fetchResponse)
你可以阅读 React 源代码
ReactComponent.prototype.setState = function (partialState, callback){
!(typeof partialState === 'object' || typeof partialState === 'function' || partialState == null) ? process.env.NODE_ENV !== 'production' ? invariant(false, 'setState(...): takes an object of state variables to update or a function which returns an object of state variables.') : _prodInvariant('85') : void 0;
this.updater.enqueueSetState(this, partialState);
if (callback) {
this.updater.enqueueCallback(this, callback, 'setState');
}
};
enqueueCallback: function (publicInstance, callback, callerName) {
ReactUpdateQueue.validateCallback(callback, callerName);
var internalInstance = getInternalInstanceReadyForUpdate(publicInstance);
if (!internalInstance) {
return null;
}
if (internalInstance._pendingCallbacks) {
internalInstance._pendingCallbacks.push(callback);
} else {
internalInstance._pendingCallbacks = [callback];
}
enqueueUpdate(internalInstance);
}
function enqueueUpdate(internalInstance) {
ReactUpdates.enqueueUpdate(internalInstance);
}
所以,我想你的回调是这样的:
this.setState({
searchKey:"BBQ"
}, this.fetchResponse)