为什么React.Memo()一直呈现我的组件



为了更深入地了解React.Memo(),我做了一个例子。

我试图将字符串从parent传递到child。然后,除了第一个默认渲染外,组件不会被渲染。

但是当我将arrayparent传递到child时,组件会重新渲染。

那么为什么组件在传递arraysobjects时保持重新渲染,而在传递string时不重新渲染呢?

是否与javascriptreference valuesprimitive values有关?

下面是我要做的代码。

parent:

import Child from "./Child";
export default function App() {
const name = {
firstName: "Amr"
};
return <Child name={name} />;
}

Child

import React from "react";
const Child = ({ name }) => {
const name1 = "Amr";
const name2 = "Amr";
// console.log(name1 === name2);
const obj1 = {
name: "Mohamed"
};
const obj2 = {
name: "Mohamed"
};
const arr1 = ["Amr"];
const arr2 = ["Amr"];
console.log(arr1 === arr2);
// console.log(obj1 === obj2); => obj1 => refrence number 1
// obj2 => refrence number 2
// 1 === 2;
// false
areEqual(name, {
firstName: "Amr"
});
return <h2>{name.firstName}</h2>;
};
// javascript [] {} => refrence value
// javascript '' or anythinng primtive value;
// obj1 = 1, obj2 = 2;
// obj1 === obj2 result false 1 === 2
function areEqual(prevProps, nextPops) {
if (prevProps === nextPops) {
console.log("equal");
} else {
console.log("not equal");
}
}
export default React.memo(Child, areEqual);

我还使用了一个函数areEqual,它根据prevPropsnextProps是否相等返回truefalse

当我传递一个String时,这个函数已经为我返回true,当我传递一个array时,这个函数已经返回false

所以,我是对的还是少了什么。

感谢更新:

如果我提到的是正确的,那么React.memo()将是无用的。

是这样吗?

默认情况下,React.memo()会对道具和道具的对象进行浅层比较——这就是为什么当道具为'object'类型时你会遇到渲染,因为引用在每个渲染上都重新创建。

React.memo接收两个参数(第二个是可选的),第二个是自定义的相等函数,你可以使用它来稳定渲染时,有道具作为非原语值。例如,你可以这样做:React.memo(SomeComponent, (prevProps, currentProps) => isDeepEqual(prevProps.someObject, currentProps.someObject)).

意味着React.memo不是无用的,它只是默认情况下使用浅比较,但也为您提供了提供自定义相等检查器的可能性,您可能想要在示例中使用。要么在React中使用深度平等检查。或者,你应该通过用useMemo包装它们的值来稳定父组件中的props。

这取决于它们的父组件,有时是必要的React.memo但在你的例子中,就像你说的,每次你定义一个数组或对象时,它的引用都会改变。我建议你使用React.useMemo。例如:

const user = React.useMemo(() => {
return {
firstName: "Amr"
}
}, []); // Second parameter works same as useCallback

反应。memo不会重新渲染组件,因为user道具没有改变