Vue2.x源码解析(一)

Vue.js 2.0 的基础

Vue.js 2.0 的基础可以概括为以下几点:

  1. 数据响应式。
  2. 组件化。
  3. 指令系统。

一个 Vue.js 应用程序由多个 Vue 实例组成,每个 Vue 实例都代表一个特定的区域内的视图,Vue 实例包含了一个数据模型和一个视图模板。Vue.js 的核心是数据响应式,也就是当我们改变数据时,视图会自动更新。

Vue.js 的源码结构

Vue.js 源码非常庞大,整个源码包括以下几个部分:

  1. Observer:用于实现数据响应式的核心组件。
  2. Watcher:用于处理视图中具体的更新操作。
  3. Compiler:用于将组件模板编译成渲染函数。
  4. Runtime:用于实现组件和指令等运行时的公共逻辑。
  5. Platform:用户平台特定的逻辑。

Vue.js 源码解析

在整个 Vue.js 源码中,Observer 和 Watcher 是比较核心和重要的两个部分。

  1. Observer

Observer 的主要作用是实现数据响应式机制,它通过递归的方式对数据对象进行劫持。当数据对象的某个属性发生变化时,会自动通知上层依赖进行更新。

Observer 的实现代码如下:

class Observer {
  constructor(value) {
    this.value = value
    this.dep = new Dep()

    // 如果该对象不可扩展,则直接返回。
    if (!Array.isArray(value)) {
      this.walk(value)
    }
  }

  /**
   * 循环遍历对象的每个属性,使得每个属性都成为响应式的。
   */
  walk(obj) {
    const keys = Object.keys(obj)
    for (let i = 0; i < keys.length; i++) {
      defineReactive(obj, keys[i], obj[keys[i]])
    }
  }
}

/**
 * 对一个对象的属性进行劫持,即实现数据响应式机制。
 */
function defineReactive(obj, key, val) {
  const dep = new Dep()

  Object.defineProperty(obj, key, {
    enumerable: true,
    configurable: true,
    get: function reactiveGetter() {
      if (Dep.target) {
        dep.depend()
      }
      return val
    },
    set: function reactiveSetter(newVal) {
      if (newVal === val) {
        return
      }
      val = newVal
      dep.notify()
    }
  })
}

 2. Watcher

Watcher 的主要作用是收集依赖,并在数据变化时触发相应的更新操作。当一个组件初始化完毕时,会创建一个渲染 Watcher,它会在组件触发更新时执行渲染函数,并进行更新操作。

Watcher 的实现代码如下:

class Watcher {
  constructor(vm, expOrFn, callback) {
    this.vm = vm
    this.callback = callback
    this.depIds = {}

    if (typeof expOrFn === 'function') {
      this.getter = expOrFn
    } else {
      this.getter = parsePath(expOrFn)
    }

    // 在实例化 Watcher 对象时,将它自身赋值给 Dep.target,此时
    // Dep.target 维护了一个栈结构。
    Dep.target = this
    this.value = this.get()
    Dep.target = null
  }

  /**
   * 收集依赖。
   */
  addDep(dep) {
    if (!this.depIds.hasOwnProperty(dep.id)) {
      dep.addSub(this)
      this.depIds[dep.id] = dep
    }
  }

  /**
   * 计算表达式的值并返回。
   */
  get() {
    // 当计算表达式的值时,依赖会被自动收集。
    return this.getter.call(this.vm, this.vm)
  }

  /**
   * 当表达式的值发生变化时会被调用,调用一系列的回调函数进行更新操作。
   */
  update() {
    const oldValue = this.value
    this.value = this.get()
    this.callback.call(this.vm, this.value, oldValue)
  }
}

/**
 * 将字符串路径解析成函数。
 */ 
function parsePath(path) {
  const segments = path.split('.')
  return function(obj) {
    for (let i = 0; i < segments.length; i++) {
      if (!obj) return
      obj = obj[segments[i]]
    }
    return obj
  }
}

代码展示

下面是一个简单的代码示例,它可以在控制台中输出 data 对象中 count 属性的值以及更新后的值:

<body>
  <div id="app">
    {{ count }}
  </div>
</body>

<script>
  const data = { count: 0 }

  new Vue({
    el: '#app',
    data: data
  })

  // 修改 count 属性的值,触发更新操作。
  data.count = 1
</script>

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Vue2.x和Vue3.x是Vue.js的两个主要版本。Vue2.x是目前国内市场上最流行的前端应用开发框架之一,而Vue3.x则是最新版本。Vue2.x的官方文档可以在https://v2.cn.vuejs.org找到,而Vue3.x的官方文档可以在https://cn.vuejs.org找到。\[1\] 使用Vue2.x的步骤如下: 1. 下载Vue.jsVuex模块。 2. 创建一个store文件夹,并在其中创建store.js文件,引入VueVuex。 3. 使用Vue.use引入Vuex。 4. 在main.js中引入store,并在实例化Vue对象时加入store对象。 5. 在组件中可以通过this.$store来使用store实例。\[2\] 在Vue2.x中,可以通过注册全局的方式来使用Vuex。在main.js中引入store,并在实例化Vue对象时加入store对象,然后就可以在组件中通过this.$store来使用store实例。\[2\] 在Vue3.x中,可以使用单库模式进行初始化。首先安装Vuex模块,然后在store/index.js中引入VueVuex,并使用Vue.use引入Vuex。在入口文件中引入store,并在实例化Vue对象时加入store对象。然后就可以在组件中通过this.$store来使用store实例。\[3\] #### 引用[.reference_title] - *1* [Vue2.x基础](https://blog.csdn.net/weixin_52218117/article/details/127270468)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v91^control_2,239^v3^insert_chatgpt"}} ] [.reference_item] - *2* *3* [Vue系列之---vue2.0 Vuex](https://blog.csdn.net/duanhy_love/article/details/103148874)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v91^control_2,239^v3^insert_chatgpt"}} ] [.reference_item] [ .reference_list ]

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值