React与Vue有什么异同

framework

相似之处

React 和 Vue 有许多相似之处,它们都有:

  • 使用 Virtual DOM
  • 提供了响应式 (Reactive) 和组件化 (Composable) 的视图组件。
  • 将注意力集中保持在核心库,而将其他功能如路由和全局状态管理交给相关的库

状态改变与重新渲染

  • 在 React 应用中,当某个组件的状态发生变化时,它会以该组件为根,重新渲染整个组件子树。我们需要通过一些手动添加手段来控制子组件的渲染过程:
    • 要避免不必要的子组件的重渲染,可以使用PureComponent或者定义shouldComponentUpdate,可能会需要使用不可变的数据结构来使得你的组件更容易被优化
  • Vue组件的依赖是在渲染过程中自动追踪的,通过 getter/setter 以及一些函数的劫持,系统能精确知晓哪个组件确实需要被重渲染,不需要考虑渲染中的优化

HTML & CSS

  • 在 React 中,一切都是 JavaScript。不仅仅是 HTML 可以用 JSX 来表达,CSS 也可以纳入到 JavaScript 中来处理
  • Vue 提供了模板,同时也支持 JSX和渲染函数。对于偏视图表现的 (presentational)推荐使用模板,对于偏逻辑的 (logical)推荐使用JSX或渲染函数
    //Vue
    <ul>
    <pasta-item v-for="(item, key) in samplePasta" :item="item" :key="key" @order="handleOrder(key)"></pasta-item>
    </ul>
    // React
    <ul className="pasta-list">
      {
          Object.keys(this.state.pastadishes).map(key =>
              <PastaItem index={key} key={key} details={this.state.pastadishes[key]} addToOrder={this.addToOrder} orders={this.state.orders[key]} />
          )
      }
    </ul>
    

状态管理VS对象属性

  • React中的状态管理是一个关键的概念,在React中state数据是不可突变的,我们需要使用setState来更新状态
  • Vue通过一个data属性来管理数据

In most cases, the built-in state management patterns provided by the frameworks themselves are insufficient for large scale apps, and a dedicated solution like Redux or Vuex must be used –Evan You

Props

  • React和Vue中都有Props的概念,用于父组件向子组件传值,是单向数据流,在具体写法上有区别。同样都是父组件需要显式定义传入的值,Vue需要显式规定props的值,React可以直接引用
    • Vue父子组件传值模式可以表示为:Props/Event
    • Vue父子组件传值模式可以表示为:Props/Callback

生命周期

react-lifecycle

vue-lifecycle

Virtual DOM 与 Diff

Virtual DOM是一个映射真实DOM的JavaScript对象,更新一个元素是通过操作Virtual DOM而不是真实DOM来实现的。当有产生变化时,一个新的Virtual DOM对象会被创建并计算新旧Virtual DOM之间的差别,之后这些差别会应用在真实的DOM上
我们用一个简单的例子来看下,在HTML中:

<ul class="list">
  <li>item 1</li>
  <li>item 2</li>
</ul>

一个简化JS对象写法:

{
    type: 'ul',
    props: {'class': 'list'},
    children: [
        { type: 'li', props: {}, children: ['item 1'] },
        { type: 'li', props: {}, children: ['item 2'] }
    ]
}

Note: Using a Virtual DOM is only a good idea if you’ve got a large application making many updates to the UI. If you’re only updating elements infrequently it’s probably overkill and could very likely be slower than updating the DOM directly.

具体地,React的Diff原理

原生应用

  • React的原生集成使用React Native
  • Vue使用Weex

全局状态管理

Redux和Vuex都是基于Flux数据通信模式实现的插件,用于多视图共享状态
flux

vuex

React的Diff原理

React基于两点假设,实现了一个启发的O(n)算法:

  • 两个不同类型的元素将产生不同的树
  • 开发者可以使用key属性来提示哪些子元素贯穿不同渲染是稳定的

算法:

  • 当差分两棵树时,React首先根据根元素类型的不同比较两个根元素
  • 不同类型的元素:每当根元素有不同类型,React将拆除旧树并且从零开始重新构建新树当拆除一棵树时,旧的DOM节点被销毁。组件实例经历钩子componentWillUnmount()componentDidMount()任何与旧树有关的状态都被丢弃
  • 相同类型的DOM元素
    • 观察二者的属性(attributes):保持相同的底层DOM节点,并仅更新变化的属性
  • 相同类型的组件元素:当组件更新时,实例保持相同,这样状态跨渲染被维护。React通过更新底层组件实例的属性(props)来匹配新元素,并在底层实例上调用componentWillReceiveProps()componentWillUpdate()
  • 子代们上的递归:当递归DOM节点的子节点时,React就是迭代在同一时间点的两个子节点列表
  • Keys:当子节点有key时,React使用key来匹配原始树的子节点和随后树的子节点
  • 采取diff算法比较新旧节点的时候,比较只会在同层级进行, 不会跨层级比

更多地,推荐一篇文章
Vue的Diff原理和React差不多


未完待续,后面可能通过代码重构,来比较两种框架的代码量和响应速度

参考及翻译原文


  转载请注明: Blog React与Vue有什么异同

 上一篇
React学习(四)实现组件关注分离 React学习(四)实现组件关注分离
Container-Component模式在开发中,可能会经常遇到两个页面或者区域展示的文档结构和样式是相同的,但数据源和交互不同。该情况下如何左到最大化的功能复用呢?——将展示部分抽离,数据和交互部分分开 Container:容器组件,
2019-02-23
下一篇 
React学习(三)更多特性 React学习(三)更多特性
props.children使代码更加优雅 当需要编写一个容器类组件,我们需要把内容传入容器,一个通用写法是class Container extends React.Component { render(){ return(
2019-02-12
  目录