工作中的那点事之 性能优化


工作中的那点事之 性能优化

无效渲染

一开始想写一下总结的,工作中重构项目用到了一些无效渲染优化。但是后面看到下面的文章,已经总结的很好了

react 无效渲染优化–工具篇
请删掉 99%的 useMemo
One simple trick to optimize React re-renders

memo的第二个参数

一般情况下不会用到。使用会有风险,自定义浅比较如果漏掉了相关属性,会导致组件的状态不改变。

memo默认情况下,判断需不需要rerender通过shadowEqual来进行浅比较,不过只会比较第一层。数据结构很深,可以通过第二个参数手动进行浅比较。

如:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
import { memo, useState } from "react";

interface ComponentProps {
config: {
user: {
name: string;
age: number;
other: string;
};
};
}

export const Component = memo(
(props: ComponentProps) => {
const {
config: { user },
} = props;

const { name, age } = user;

console.log("rerender");

return (
<>
<div>{name}</div>
<div>{age}</div>
</>
);
},
(prevProps, nextProps) => {
return (
prevProps.config.user.name === nextProps.config.user.name &&
prevProps.config.user.age === nextProps.config.user.age
);
}
);

export default function Home() {
const [compProps, setCompProps] = useState<ComponentProps>({
config: {
user: {
name: "clz",
age: 24,
other: "hello",
},
},
});

return (
<>
<Component {...compProps} />

<div>{compProps.config.user.other}</div>

<div className="btn-container">
<button
onClick={(): void => {
setCompProps({
config: {
user: {
...compProps.config.user,
name: "ccc",
},
},
});
}}
>
change name
</button>
<button
onClick={(): void => {
setCompProps({
config: {
user: {
...compProps.config.user,
other: "hi",
},
},
});
}}
>
change other
</button>
</div>
</>
);
}

上面的例子中,父组件改变other的值也不会触发User组件的rerender。如果把memo的第二个参数去掉,则会触发Userrerender

组件懒加载

lazySuspense联合使用。

1
2
3
4
5
6
7
8
9
10
11
import { lazy, Suspense } from "react";

const Home = lazy(() => import("./components/Home"));

export default function App() {
return (
<Suspense fallback="loading">
<Home />
</Suspense>
);
}

使用Suspense可以在等待加载lazy组件时,显示加载内容,如上面的loading文案。

还可以封装成一个公共方法。

1
2
3
4
5
6
7
8
9
10
11
import { lazy, ReactElement, Suspense } from "react";

const Home = lazy(() => import("./components/Home"));

const withLoadingComponent = (component: ReactElement) => (
<Suspense fallback="loading">{component}</Suspense>
);

export default function App() {
return withLoadingComponent(<Home />);
}

文章作者: 赤蓝紫
版权声明: 本博客所有文章除特別声明外,均采用 CC BY 4.0 许可协议。转载请注明来源 赤蓝紫 !
评论
  目录