[React] Preventing extra re-rendering with function component by using React.memo and useCallback
Got the idea form this lesson. Not sure whether it is the ncessary, no othere better way to handle it.
Have a TodoList component, every time types in NewTodo input fields, will trigger the re-rendering for all components.
import React, { useState, useContext, useCallback } from "react";
import NewTodo from "./NewTodo";
import TodoItem from "./TodoItem5";
import { Container, List } from "./Styled";
import About from "./About";
import { useTodosWithLocalStorage, useKeyDown } from "./hooks";
import { useTitle as useDocumentTitle } from "react-use";
import ThemeContext from "./ThemeContext";
const incompleteTodoCount = todos =>
todos.reduce((memo, todo) => (!todo.completed ? memo + 1 : memo), 0);
export default function TodoList() {
const [newTodo, updateNewTodo] = useState("");
const [todos, dispatch] = useTodosWithLocalStorage([]);
const inCompleteCount = incompleteTodoCount(todos);
const title = inCompleteCount ? `Todos (${inCompleteCount})` : "Todos";
useDocumentTitle(title);
let [showAbout, setShowAbout] = useKeyDown(
{ "?": true, Escape: false },
false
);
const handleNewSubmit = e => {
e.preventDefault();
dispatch({ type: "ADD_TODO", text: newTodo });
updateNewTodo("");
};
const theme = useContext(ThemeContext);
return (
<Container todos={todos}>
<NewTodo
onSubmit={handleNewSubmit}
value={newTodo}
onChange={e => updateNewTodo(e.target.value)}
/>
{!!todos.length && (
<List theme={theme}>
{todos.map(todo => (
<TodoItem
key={todo.id}
todo={todo}
onChange={id => dispatch({ type: "TOGGLE_TODO", id })}
onDelete={id => dispatch({ type: "DELETE_TODO", id })}
/>
))}
</List>
)}
<About isOpen={showAbout} onClose={() => setShowAbout(false)} />
</Container>
);
}
The way to solve the problem is
1. For every callback:
<TodoItem
onChange={id => dispatch({ type: "TOGGLE_TODO", id })}
onDelete={id => dispatch({ type: "DELETE_TODO", id })}
/> <About isOpen={showAbout} onClose={() => setShowAbout(false)} />
We should replace with useCallback hooks:
const handleChange = useCallback(
id => dispatch({ type: "TOGGLE_TODO", id }),
[]
);
const handleDelete = useCallback(
id => dispatch({ type: "DELETE_TODO", id }),
[]
); const handleClose = userCallback(
() => setShowAbout(false), []
)
{!!todos.length && (
<List theme={theme}>
{todos.map(todo => (
<TodoItem
key={todo.id}
todo={todo}
onChange={handleChange}
onDelete={handleDelete}
/>
))}
</List>
)}
<About isOpen={showAbout} onClose={handleClose} />
This helps to reduce some extra re-rendering.
2. Using Reac.memo for function component:
import React, { useContext } from "react";
import Checkbox from "./Checkbox";
import ThemeContext from "./ThemeContext";
import { Button, Item } from "./Styled";
const TodoItem = React.memo(({ todo, onChange, onDelete }) => {
console.log("TodoItem5", { todo, onChange, onDelete });
const theme = useContext(ThemeContext);
return (
<Item key={todo.id} theme={theme}>
<Checkbox
id={todo.id}
label={todo.text}
checked={todo.completed}
onChange={onChange.bind(this, todo.id)}
/>
<Button onClick={onDelete.bind(this, todo.id)} theme={theme}>
x
</Button>
</Item>
);
});
export default TodoItem;
import React from "react";
import styled from "react-emotion"; import { Dialog } from "@reach/dialog"; ... export default React.memo(function TodoItem({ isOpen, onClose }) {
return (
<Dialog isOpen={isOpen}>
...
</Dialog>
);
});
Assume that every times I should wrap function component with React.memo() and use useCallback whenever necessary.
[React] Preventing extra re-rendering with function component by using React.memo and useCallback的更多相关文章
- [React] Write a stateful Component with the React useState Hook and TypeScript
Here we refactor a React TypeScript class component to a function component with a useState hook and ...
- 精读《Function Component 入门》
1. 引言 如果你在使用 React 16,可以尝试 Function Component 风格,享受更大的灵活性.但在尝试之前,最好先阅读本文,对 Function Component 的思维模式有 ...
- [React] Preview and edit a component live with React Live
In this lesson we'll use React Live to preview and edit a component directly in the browser. React L ...
- [React] Forward a DOM reference to another Component using forwardRef in React 16.3
The function forwardRef allows us to extract a ref and pass it to its descendants. This is a powerfu ...
- 3.React Native在Android中自己定义Component和Module
React Native终于展示的UI全是Native的UI.将Native的信息封装成React方便的调用. 那么Native是怎样封装成React调用的?Native和React是怎样交互的? V ...
- React报错之React Hook 'useEffect' is called in function
正文从这开始~ 总览 为了解决错误"React Hook 'useEffect' is called in function that is neither a React function ...
- [React & Debug] Quick way to debug Stateless component
For example we have the following code: const TodoList = (props) => ( <div className="Tod ...
- react 使用react-router-dom 在Route对象上component 参数接收的是一个方法而非一个对象
其实对于jsx语法 一直觉的它有点清晰都不是很好,js和html混在一起有点不伦不类的样子,以下是我在使用react中遇到的一个很奇葩的事情 假定你定义了一个component Mine import ...
- 《React Native 精解与实战》书籍连载「React Native 底层原理」
此文是我的出版书籍<React Native 精解与实战>连载分享,此书由机械工业出版社出版,书中详解了 React Native 框架底层原理.React Native 组件布局.组件与 ...
随机推荐
- Mybatis源码分析之参数处理
Mybatis对参数的处理是值得推敲的,不然在使用的过程中对发生的一系列错误直接懵逼了. 以前遇到参数绑定相关的错误我就是直接给加@param注解,也稀里糊涂地解决了,但是后来遇到了一些问题推翻了我的 ...
- 小数据池,bytes
'''python2 python3 '''#python2#print() print 'abc'#range() xrange() 生成器# raw_input() #python3#print( ...
- 【BZOJ 3235】 3235: [Ahoi2013]好方的蛇 (单调栈+容斥原理)
3235: [Ahoi2013]好方的蛇 Time Limit: 10 Sec Memory Limit: 64 MBSubmit: 187 Solved: 95 Description 有一天, ...
- [bzoj1019][SHOI2008]汉诺塔 (动态规划)
Description 汉诺塔由三根柱子(分别用A B C表示)和n个大小互不相同的空心盘子组成.一开始n个盘子都摞在柱子A上,大的在下面,小的在上面,形成了一个塔状的锥形体. 对汉诺塔的一次合法的操 ...
- Codeforces Round #302 (Div. 1) C. Remembering Strings DP
C. Remembering Strings Time Limit: 20 Sec Memory Limit: 256 MB 题目连接 http://codeforces.com/contest/5 ...
- 最新iOS砸壳方式Frida (Mac OSX)
1. 安装Frida 首先需要安装Python3,我下载的是 macOS 64-bit installer 安装,因Macbook本机自带python为2.7.x,故需要配置~/.bash_profi ...
- mysql 存储过程案列一个。
-- 设置分隔符 DELIMITER // /*初始化*/ DROP PROCEDURE IF EXISTS useCursor // /*建立 存储过程 create */ CREATE PROCE ...
- 配置Maven环境变量与Intelij IDE配置Maven
Maven有什么用? 以前我们导入第三方jar包的流程是什么?一般是download,然后copy到项目中,然后依赖(library)项目,最后被我们使用. 通俗的说,就是不用我们自己去downloa ...
- C# winform 禁止窗体移动
#region 禁止窗体移动 public const int WM_SYSCOMMAND = 0x112; public const int SC_MOVE = 0xF012; protected ...
- CentOS下KVM克隆完成后修改MAC地址/VMware复制虚拟机修改MAC地址
克隆完成之后可能mac地址会有冲突,进入KVM删除/etc/udev/rules.d/70-persistent-net.rules中的eth0的配置,接着把eth1改成eth0,并且修改/etc/s ...