我的组件等效于此:
const PickAShell = () => {
const [functionToRun, setFunctionToRun] = useState(() => {});
const [shellPicked, setShellPicked] = useState(0);
const shells = [1,2,3,4,5];
const pickShellFn = (shellNumber, onConfirm) => {
setFunctionToRun(onConfirm);
setShellPicked(shellNumber);
}
const win = () => setShellPicked(0)
&& alert('You Win');
const lose = (shellNumber) => setShellPicked(0)
&& alert('nothing under shell '+shellNumber)
return (
<div>
{shells.map(shellNumber => {
const clickHandler = shellNumber%2?
() => pickShellFn(shellNumber, () => win())
: () => pickShellFn(shellNumber, () => lose(shellNumber));
return <Button onClick={clickHandler}>{`pick shell number ${shellNumber}`}</Button>
}) }
{shellPicked? (<Button onClick={functionToRun}>Reveal Shell</Button>): null}
</div>
)
}
我看到的是,当我运行它时,我单击"挑选壳号x"按钮的等效词,然后运行功能(赢/丢失(。
在Chrome Dev工具中,它调用" setFunctionTorun",并立即调用该函数(丢失(。
我期望的是,单击"选择shell编号2"按钮后,它应该将functionToRun
设置为() => win()
脂肪箭头功能。然后,只有在单击"显示shell"按钮时才能调用任何东西。
解决方案是使clickhandler这样:
const clickHandler = shellNumber%2?
() => pickShellFn(shellNumber, () => () => win())
: () => pickShellFn(shellNumber, () => () => lose(shellNumber));
现在,当函数称为函数时,它返回内部函数,准备通过"启示"按钮调用。
这是因为useState
可以使用功能
setPartOfState(prevState => doSomethingWith(previousState))
这意味着替代方案是呼叫:
,而不是上述。setFunctionToRun(() => onConfirm);
使用相同的签名,但不使用先前的状态或调用onConfirm
。如果此不存在此匿名函数,则此时会调用onConfirm
,而不仅仅是传递。