首页 > 解决方案 > 为什么使用无状态功能组件而不是基于类的组件?

问题描述

我正在学习 ReactJS,并且我了解到有 UI 组件和容器组件。容器组件是使用classes扩展React.Component和包含state以及良好的旧render方法实现的,而 UI 组件是使用创建的functions,它们只关心 UI,因为它们只从props.

示例无状态功能组件:

const Ninjas = (props) => {
    const { ninjas } = props;

    const ninjalist = ninjas.map((x) => {
        var divStyle = {
            color: getRandomColor(),
        };

        return (
            <div className="ninja" key={x.key} style={divStyle}>
                <p>Name: {x.name}</p>
                <p>Age: {x.age}</p>
                <p>Belt: {x.belt}</p>
            </div>
        );
    });
    return <div className="ninja-list">{ninjalist}</div>;
};

export default Ninjas;

与容器组件相同的示例

export default class Ninjas extends Component {
    getRandomColor = () => {
        ....
        return color;
    };

    render() {
        const { ninjas } = this.props;

        const ninjalist = ninjas.map((x) => {
            var divStyle = {
                color: this.getRandomColor(),
            };

            return (
                <div className="ninja" key={x.key} style={divStyle}>
                    <p>Name: {x.name}</p>
                    <p>Age: {x.age}</p>
                    <p>Belt: {x.belt}</p>
                </div>
            );
        });
        return <div className="ninja-list">{ninjalist}</div>;
    }
}

所以我的问题是,当我们可以轻松地完成与容器组件相同的事情时,为什么我们还要费心制作 UI 组件(不使用render容器组件中使用的方法)。

标签: javascriptreactjscomponents

解决方案


功能性无状态组件(您错误地称为 UI 组件,所有组件都是有状态和无状态的 UI 组件)只是创建组件的一种简写方法,这些组件仅基于传递的 props 呈现某些内容,并且不需要保持内部状态.

当然,人们总是可以使用基于类的组件来扩展React.Component. 但是,如果可以的话,为什么不使用快捷方式来节省时间和空间并简化事情。没有什么强迫您创建功能组件,您始终可以使用基于类的组件,除非您需要简化并节省时间和空间。

根据React文章中的功能与类组件:

那么我为什么要使用函数式组件呢?

你可能会问自己,如果函数式组件删除了这么多好的特性,为什么还要使用它们。但是在 React 中使用函数式组件有一些好处:

  1. 函数式组件更容易阅读和测试,因为它们是没有状态或生命周期钩子的纯 JavaScript 函数
  2. 你最终得到的代码更少
  3. 它们帮助您使用最佳实践。分离容器和展示组件会变得更容易,因为如果您无法访问组件中的 setState(),则需要更多地考虑组件的状态
  4. React 团队提到,在未来的 React 版本中,功能组件可能会有性能提升

我要添加第五点,即提供直接访问 DOM 节点的功能的React 引用(使用 React 16.3+)不能与功能组件一起使用。

在 React v.16.8+中引入了useState钩子,它使功能组件能够在保持功能的同时保持状态。

此外,随着React.memo 高阶组件的引入,我们可以使用 memoization 来避免重新渲染功能组件,因为它为相同的道具渲染相同的东西(浅度测试差异)


推荐阅读