const {useRef, useState} = React;
function List(){
const renderCount = useRef(0);
console.log('<List /> is rendered', ++renderCount.current);
const [isClicked, setIsClicked] = useState(false);
const toggle = () => setIsClicked(!isClicked)
return (
<div>
<ButtonA onClick={toggle} isClicked={isClicked} />
<ButtonB />
</div>
)
}
function ButtonA(props){
const renderCount = useRef(0);
console.log('<ButtonA /> is rendered', ++renderCount.current);
return (<button onClick={props.onClick} className={`${props.isClicked ? 'true':'false'}`} >Button A</button>);
}
function ButtonB(){
const renderCount = useRef(0);
console.log('<ButtonB /> is rendered', ++renderCount.current);
return (<button>Button B </button>);
}
ReactDOM.render(
<List />, document.getElementById('root')
)
button.true{
background-color: red;
}
button.false{
background-color: blue;
}
<script crossorigin src="https://unpkg.com/react@16/umd/react.development.js"></script>
<script crossorigin src="https://unpkg.com/react-dom@16/umd/react-dom.development.js"></script>
<div id="root"></div>
这是示例代码。
当我单击<ButtonA />
时,我希望重新渲染<List />
和<Button A/>
,但是<ButtonB />
也被重新渲染。
当我单击<ButtonB />
时,我想阻止重新渲染<ButtonA />
我该如何实现?
答案 0 :(得分:2)
对于功能组件,您可以使用React.memo
来具有与shouldComponentUpdate
相同的功能
const {useRef, useState} = React;
function List(){
const renderCount = useRef(0);
console.log('<List /> is rendered', ++renderCount.current);
const [isClicked, setIsClicked] = useState(false);
const toggle = () => setIsClicked(!isClicked)
return (
<div>
<ButtonA onClick={toggle} isClicked={isClicked} />
<ButtonB />
</div>
)
}
function ButtonA(props){
const renderCount = useRef(0);
console.log('<ButtonA /> is rendered', ++renderCount.current);
return (<button onClick={props.onClick} className={`${props.isClicked ? 'true':'false'}`} >Button A</button>);
}
const ButtonB = React.memo(() => {
const renderCount = useRef(0);
console.log('<ButtonB /> is rendered', ++renderCount.current);
return (<button>Button B </button>);
})
ReactDOM.render(
<List />, document.getElementById('root')
)
button.true{
background-color: red;
}
button.false{
background-color: blue;
}
<script crossorigin src="https://unpkg.com/react@16/umd/react.development.js"></script>
<script crossorigin src="https://unpkg.com/react-dom@16/umd/react-dom.development.js"></script>
<div id="root"></div>
答案 1 :(得分:0)
优化功能组件以使React可以将其视为纯组件,不一定需要将该组件转换为类组件。
如果您已经熟悉了recompose软件包,那么您会知道它提供了大量的高阶组件,这在处理功能组件时非常有用。
recompose包导出一个{pure}高阶组件,该组件试图通过阻止对组件的更新(除非道具已更改)来优化React组件,除非使用propeEqual()来测试更改。
使用纯的高阶组件,我们的功能组件可以包装如下:
import React from 'react';
import { pure } from 'recompose';
function ButtonB() {
const renderCount = useRef(0);
console.log('<ButtonB /> is rendered', ++renderCount.current);
return (<button>Button B </button>);
}
// Wrap component using the `pure` HOC from recompose
export default pure(ButtonB);
答案 2 :(得分:0)
默认情况下,如果父级的状态发生更改,则会重新渲染父级的所有子级。此更改是否对孩子有直接影响都没有关系。 但是,您可以使用shouldComponentUpdate生命周期方法显式禁用特定组件的重新渲染。
docker commit [OPTIONS] CONTAINER [REPOSITORY[:TAG]]
class Button extends React.Component {
shouldComponentUpdate(){
return !this.props.shouldNotUpdate;
}
render(){
const { id, onClick } = this.props;
console.log(`button ${this.props.id} rendered`)
return <button onClick={onClick}>{`Button ${id}`}</button>
}
}
class App extends React.Component {
state = { clicked: 0 }
handleClick = () => this.setState(({clicked}) => ({clicked: clicked + 1}))
render(){
return (
<div>
{this.state.clicked}<br />
<Button id="1" onClick={this.handleClick} />
<Button id="2" shouldNotUpdate />
</div>
)
}
}
ReactDOM.render(<App />, document.getElementById('root'));