能否在条件语句中使用 useMemo 钩子?

9

我曾试图在条件语句中使用React Hooks,但不幸的是,React几乎对所有Hooks都给出了错误提示,这正是Hooks哲学所期望的。

后来我尝试在else语句中使用useMemo Hook,结果没有错误提示。我搜索了一些关于这个差异的资料,但并未发现有什么有希望的结果。

我的问题是,useMemo是否是一个例外,可以在条件语句中使用useMemo?

1个回答

17

不,你不能在条件语句中运行useMemo或其他任何React hooks。同样的React hooks必须每次组件渲染时按相同的顺序调用。在我看来,hooks的工作方式确实很反直觉,这也是使React变得难以学习的主要原因之一。

有两种可能的解决方法,一种是将条件移动到hook回调内部,另一种是将代码移动到单独的组件中。

采用这个例子:

function MyComponent() {
    if (condition) {
        const myVar = useMemo(() => { return value; }, [value]);
        return <OtherComponent var={myVar}/>;
    } else {
        return <SomethingElse/>;
    }
}

一种替代方案是:

function MyComponent() {
    const myVar = useMemo(() => {
        if (condition) {
            return value;
        }
    }, [condition, value]);

    if (condition) {
        return <OtherComponent var={myVar}/>;
    } else {
        return <SomethingElse/>;
    }
}

另一种选择可能是:

function MyComponent() {
    if (condition) {
        return <MyComponent2/>;
    } else {
        return <SomethingElse/>;
    }
}

function MyComponent2() {
    const myVar = useMemo(() => { return value; }, [value]);
    return <OtherComponent var={myVar}/>;
}

是的,我正在使用第二种选择。那看起来更自然。 当我在else语句中使用useMemo钩子时,我很惊讶它没有给我错误。 - Sujan Thakare
2
如果在if块中恰好有一个useMemo调用,在else块中也恰好有一个useMemo调用,React可能不会注意到它们是不同的,因为它只能检测钩子的数量和类型以及它们被调用的顺序。所以它可能不会抛出异常,但它可能不会按照你的意图工作。 - cdauth

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接