Vue 2.0中实现双向绑定的原理是什么

  介绍

这篇文章将为大家详细讲解有关Vue 2.0中实现双向绑定的原理是什么,文章内容质量较高,因此小编分享给大家做个参考,希望大家阅读完这篇文章后对相关知识有一定的了解。

<强> 1,定义构造函数

function  Vue(选项){   这。el 美元;=,document.querySelector (option.el);,//获取挂载节点   这。data 美元;=,option.data;   这。methods 美元;=,option.methods;=,this.deps ,{},,//所有订阅者集合,目标格式(一对多的关系):{味精:[订阅者1,订阅者2,订阅者3],,信息:,(订阅者1,订阅者2]}   ,this.observer (。$ data);,//调用观察者   ,this.compile(这一点。el美元);,//调用指令解析器   }

<强> 2,定义指令解析器

Vue.prototype.compile =, function  (el), {   ,let  nodes =, el.children;,//获取挂载节点的子节点   ,for  (var 小姐:=,0;,小姐:& lt;, nodes.length;,我+ +),{   节点,var  node =,(我);   ,if  (node.children.length), {   ,this.compile(节点),//递归获取子节点   ,}   ,if  (node.hasAttribute (& # 39; l-model& # 39;)),{,//当子节点存在l型指令   ,let  attrVal =, node.getAttribute (& # 39; l-model& # 39;);,//获取属性值   ,node.addEventListener(& # 39;输入# 39;,,((),=祝辞,{   ,this.deps [attrVal] .push (new 观察者(节点,“value",,这个,,attrVal)),,//添加一个订阅者=,let  thisNode 节点;   ,return (),=祝辞,{   这才能。$ data [attrVal],=, thisNode.value //更新数据层的数据   ,}   ,})())   ,}   ,if  (node.hasAttribute (& # 39; l-html& # 39;)), {   ,let  attrVal =, node.getAttribute (& # 39; l-html& # 39;);,//获取属性值   ,this.deps [attrVal] .push (new 观察者(节点,“innerHTML",,这个,,attrVal)),,//添加一个订阅者   ,}   ,if  (node.innerHTML.match (/{{((^ \ {| \}] +)}}/)), {   ,let  attrVal =, node.innerHTML.replace (/[{{|}}]/g, & # 39; & # 39;);,//获取插值表达式内容   ,this.deps [attrVal] .push (new 观察者(节点,“innerHTML",,这个,,attrVal)),,//添加一个订阅者   ,}   ,if  (node.hasAttribute (& # 39; l:点击# 39;)),{   ,let  attrVal =, node.getAttribute (& # 39; l:点击# 39;);,//获取事件触发的方法名   ,node.addEventListener(& # 39;点击# 39;,,这个。方法[attrVal] .bind美元($ data)),,//将这指向元数据   ,}   ,}   }

<强> 3,定义观察者

Vue.prototype.observer =,功能(数据){   ,(var  key 拷贝数据){   ,(函数(){   ,let  val =,数据(关键);,//每一个数据的属性值   ,that.deps(例子),=,[];,//初始化所有订阅者对象{味精:[订阅者),,信息:,[]}   ,var  watchers =, that.deps(例子);   ,Object.defineProperty(数据,键,,{,//数据劫持   ,得到:函数(){   return 才能,val;   },   ,集:函数(newVal){,//设置值(说明有数据更新)   如果才能(val  !==, newVal) {   时间=val 才能;newVal;   ,,}//,才能通知订阅者   watchers.forEach才能(观察家=祝辞{   watcher.update才能()   })才能   ,}   ,})   ,})(本)   ,}   }

<强> 4,定义订阅者

function 观察者(attr, el,还以为,vm, attrVal), {=,this.el  el;=,,this.attr  attr;=,this.vm 虚拟机;=,,this.val  attrVal;   ,this.update();,//更新视图   }

<强> 5,更新视图

Watcher.prototype.update =, function  (), {   ,this.el [this.attr],=this.vm。$ data [this.val]   }

以上代码定义在一个Vue。js文件中,在需要使用双向绑定的地方引入即可。

尝试使用一下:

& lt; ! DOCTYPE  html>   & lt; html  lang=癳n"祝辞   & lt; head>   ,& lt; meta  charset=癠TF-8"比;   ,& lt; meta  name=皏iewport",内容=翱矶?设备宽度,初始=1.0,比;   ,& lt; meta  http-equiv=癤-UA-Compatible",内容=癷e=edge"比;   ,& lt; title> Document   ,& lt; script  src=啊?vue.js"祝辞& lt;/script>   & lt;/head>   & lt; body>   & lt; !   ,实现mvvm的双向绑定,是采用数据劫持结合发布者——订阅者模式的方式,通过Object.defineProperty()来劫持各个属性的setter,吸气,在数据变动时发布消息给订阅者,触发相应的监听回调。就必须要实现以下几点:   ,1,实现一个数据监听器观察者,能够对数据对象的所有属性进行监听,如有变动可拿到最新值并通知订阅者   ,2,实现一个指令解析器编译、对每个元素节点的指令进行扫描和解析,根据指令模板替换数据,以及绑定相应的更新函数   ,3,实现一个观察者,作为连接观察者和编译的桥梁,能够订阅并收到每个属性变动的通知,执行指令绑定的相应回调函数,从而更新视图   ,4,mvvm入口函数,整合以上三者   ,——比;   ,& lt; div  id=癮pp"比;   ,& lt; input 类型=皌ext", l型=癿sg",在   ,& lt; p  l-html=癿sg"祝辞& lt;/p>   ,& lt; input 类型=皌ext", l型=癷nfo",在   ,& lt; p  l-html=癷nfo"祝辞& lt;/p>   ,& lt; button  l:点击=癱lickMe"在点我& lt;/button>   ,& lt; p>{{味精}}& lt;/p>   ,& lt;/div>      null   null   null   null   null   null   null   null   null   null   null   null   null   null   null   null

Vue 2.0中实现双向绑定的原理是什么