根据React Docs,我们可以有两种方式用于setState,一种是带有对象语法,另一种是带有它们的函数,它们如下所示
this.setState((prevState, props) => ({
counter: prevState.counter + props.increment
}));
我对箭头函数语法的理解就像() => {}
,其中在箭头=>
之后遵循花括号,但根据样本它是圆括号而不是花括号
这些语法()=>{}
和()=>({})
有什么区别。
在this.setStage(prevStage=>({}))
函数中使用handleClick
语法时,根据文档尝试示例代码,如果将其更改为this.setState(prevStage=>{})
,则不会切换按钮值。
以下是工作代码:
class Toggle extends React.Component {
constructor(props) {
super(props);
this.state = {
isToggleOn : true
}
this.handleClick = this.handleClick.bind(this);
}
handleClick() {
this.setState(prevState => ({
isToggleOn: !prevState.isToggleOn
}));
}
render() {
return (
<div>
<button onClick={this.handleClick}>
{this.state.isToggleOn ? 'ON' : "OFF"}
</button>
</div>
);
}
}
后来我引用了MDN并在Advanced Syntax部分下找到了详细信息,如果你想隐式返回对象,那么我们需要将它包含在()中,这回答了我的问题。
//括号化函数体以返回对象文字表达式:
params =>({foo:bar})
这里有两个主要问题需要考虑:
setState
作为参数传递时,function
期望什么?回答:
{}
)时,你会隐式返回:
const x = () => 'we are returning a string here';
当我们使用函数体时,我们需要使用return
关键字:
const x = () => {
return 'another string returned'
};
还有另一个选项可以返回没有return
关键字的东西,你可以用括号()
包裹花括号,这将向引擎发出大括号不是函数体而是一个对象的信号,这被认为是创建一个表达式:
const x = () => ({myKey: 'some string'});
这与我们通常使用函数表达式类似。
特别是IIFE(立即调用函数表达式):
(function() {
//some logic...
})();
如果我们不返回任何东西,那么函数将只返回undefined
。setState
,当您将函数作为参数传递时,它期望此函数将返回一个对象。
当你的函数没有返回任何东西时(如上所述)它实际上返回了undefined
。
JavaScript不会产生错误,因为这不是错误。它只是一个什么都不返回的函数(undefined
)。以下是没有包装括号的代码的运行示例:
class Toggle extends React.Component {
constructor(props) {
super(props);
this.state = {
isToggleOn: true
}
this.handleClick = this.handleClick.bind(this);
}
handleClick() {
this.setState(prevState => {
return { // we must return an object for setState
isToggleOn: !prevState.isToggleOn
}
});
}
render() {
return (
<div>
<button onClick={this.handleClick}>
{this.state.isToggleOn ? 'ON' : "OFF"}
</button>
</div>
);
}
}
ReactDOM.render(<Toggle />, document.getElementById('root'));
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react-dom.min.js"></script>
<div id="root"></div>
编辑 作为您的意见的后续
当我们只返回key:value而不包含括号时,我希望Javascript会抛出错误,即()=> {key:value} - 这意味着它试图返回'key:value'而不是Object,这应该是一个JS错误,但它没有抛出任何错误。如果我的理解是错误的,请纠正我
它没有返回键值,它是一个返回undefined
的“void”函数。
看到这个正在运行的代码段:
const x = () => {myKey: 'myValue'};
const y = x();
console.log(y);
编辑#2 跟进你的其他评论(在我看来,这基本上是一个完全不同的问题)。
让y = function(){'abc':1} - 语法错误,让y = function(){abc:1}并让y = function(){return {'abc':1}} - 没有错误,其中第一个(语法错误)我们试图将1分配给字符串abc,这与第3个样本(无错误)相同,第2个例子将1分配给abc - 在没有引号时起作用。请解释这三个样本的区别以及为什么第一个失败而不是第二个例子
好的,这很有意思。
我们试图将第一个(语法错误)分配给字符串abc ...
不,我们不是。
我们正在尝试创建一个label:
,但标签不能是字符串!
与变量相同不能是字符串 - var 'x' = 1
。
这是JavaScript中的有效语法:
const y = function(){b:2};
我们在这里做的是创建一个名为label:
的a
,这个标签有一个1
的表达式(我们没有对这个标签做任何事情。)。
const x = () => {a:1};
const y = function(){a:1};
此语法无效:
const y = function() { 'a': 1 };
这是无效的,因为标签不能以字符串开头:
const x = () => { 'a': 1 };
const y = function() { 'a': 1 };
再次,这不是一个key:value
对,大括号是函数的BODY。
如果你只写()=> {}这明确意味着该函数不仅仅返回一些东西。
例如:
const logAndReturn = (val) => {
console.log(val)
return val
}
但是,假设您有一个函数,它接受参数并返回基于这些参数的对象。
const createUser = (x) => {
prop: x
}
这将提示错误,因为这基本上转换为:
function createUser(x) {
prop:x
}
使用paranthesis,您仍然使用箭头函数的默认返回值。
const createUser = (name, email) => ({})
function createUser(name, email) { return {} )
简单的答案是
()=>({})
它也等于
()=> {
return {}
}
返回一个空对象,这里围绕{}
的括号表示return
。你知道我们必须将对象传递给setState
所以我们插入任何想要在{}
之间声明的东西
()=>({any thing you want to set to state})