React JS中constructor初始化state与useState的区别是什么
useState定义状态与constructor初始化状态的核心差异 你测试下来觉得二者功能效果一致,只是刚好覆盖了最基础的「给状态赋初始值」的简单场景,实际上两者从适用场景到运行逻辑都有本质区别,完全不能混用:
适用的组件类型完全不同
constructor内通过this.state初始化状态是**类组件(Class Component)**的专属语法,必须写在继承自React.Component的类结构中才能生效,配套的状态更新必须调用this.setState()方法,状态读取都要通过this.state.xxx的形式,全程依赖类实例的this上下文。useState是React 16.8之后推出的Hook API,只能在函数组件/自定义Hook的顶层作用域调用,既不能在类组件里使用,也不能放在循环、条件判断、嵌套函数里。它不需要依赖this上下文,每个调用会返回独立的状态值和对应的更新函数,直接调用更新函数就能修改对应状态。状态组织逻辑不同
类组件的this.state是一个整体对象,所有状态字段都要挂在这个对象下,调用this.setState更新时React会自动帮你做顶层属性的浅合并——比如你示例里state同时存了robots和searchfield,后续调用this.setState({searchfield: 'a'})时,不会把已有的robots字段冲掉。useState推荐按业务维度把状态拆成独立的切片,你示例里把筛选名、机器人列表拆成两个独立的useState调用,两个状态的更新完全互不干扰。当然你也可以给useState传对象存多个字段,但这时候更新不会自动合并属性,必须自己用展开运算符把旧的状态字段带上,不然会丢失未更新的字段。初始化逻辑的灵活度、性能表现不同
类组件constructor里的初始化逻辑会在类实例创建时执行一次,要获取组件入参props的话必须给constructor和super()都传入props参数,要是初始值需要复杂计算,不管计算结果后续会不会用到,实例创建时都会立刻执行计算。useState支持传入初始化函数来生成初始值,比如const [robots, setRobots] = useState(() => 复杂计算逻辑()),这个初始化函数只会在组件首次渲染的时候执行一次,后续重渲染不会重复运行,对复杂初始值场景的性能更友好;同时函数组件作用域里可以直接拿到props、组件内定义的其他常量,初始化赋值的写法更灵活。
额外提一句你贴的类组件示例代码有个小问题:robots: robots的写法会直接去当前作用域找robots变量,如果外层没定义的话会抛引用错误,对应你函数组件里的空数组初始值,这里应该写成robots: []才对。
内容的提问来源于stack exchange,提问作者John Michael Vicmudo

