深入Vue原理_雙向數據綁定(視圖/數據)

在這里插入圖片描述

歡迎各位小伙伴們!
為大家推薦一款刷題神奇哦 點擊鏈接訪問牛客網
各大互聯網大廠面試真題。從基礎到入階乃至原理刨析類面試題 應有盡有,趕快來裝備自己吧!助你面試穩操勝券,solo全場面試官

文章目錄

    • 數據的變化反應到視圖
      • 命令式操作視圖
      • 聲明式操作視圖
      • 小結
    • 視圖的變化反應到數據
    • 現存的問題
    • 寫在最后

數據的變化反應到視圖

前面我們了解到數據劫持之后,我們可以在數據發生修改之后做任何我們想要做的事情,操作視圖當然也是OK的

命令式操作視圖

目標:我們通過原始的操作dom的方式讓每一次的name的最新值都能顯示到p元素內部

<div id="app"><p></p>
</div>
<script>let data = {name: '小蘭同學',age: 18,height:180}// 遍歷每一個屬性Object.keys(data).forEach((key)=>{// key 屬性名// data[key] 屬性值defineReactive(data,key,data[key])})function defineReactive(data,key,value){Object.defineProperty(data,key,{get(){return value},set(newVal){value = newVal // 數據發生變化,操作dom進行更新document.querySelector('#app p').innerHTML = data.name}})}// 首次渲染document.querySelector('#app p').innerHTML = data.name
</script>

聲明式操作視圖

目標:我們將data中name屬性的值作為文本渲染到標記了v-text的p標簽內部,在vue中,我們把這種標記式的聲明式渲染叫做指令

<div id="app"><p v-text="name"></p>
</div>
<script>let data = {name: '小蘭同學',age: 18,height: 180}// 遍歷每一個屬性Object.keys(data).forEach((key) => {// key 屬性名// data[key] 屬性值// data 原對象defineReactive(data, key, data[key])})function defineReactive(data, key, value) {Object.defineProperty(data, key, {get() {return value},set(newVal) {value = newVal// 數據發生變化,操作dom進行更新compile()}})}// function compile() {let app = document.getElementById('app')// 1.拿到app下所有的子元素const nodes = app.childNodes   //  [text, input, text]//2.遍歷所有的子元素nodes.forEach(node => {// nodeType為1為元素節點if (node.nodeType === 1) {const attrs = node.attributes// 遍歷所有的attrubites找到 v-modelArray.from(attrs).forEach(attr => {const dirName = attr.nodeNameconst dataProp = attr.nodeValueif (dirName === 'v-text') {node.innerText = data[dataProp]}})}})}// 首次渲染compile()
</script>

小結

  1. 不管是指令也好,插值表達式也好,這些都是將數據反應到視圖的標記而已,通過標記我們可以把數據的變化響應式的反應到對應的dom位置上去
  2. 找標記,把數據綁定到dom的過程,我們稱之為binding

視圖的變化反應到數據

目標:將data中的message屬性對應的值渲染到input上面,同時input值發生修改之后,可以反向修改message的值,在vue系統中,v-model指令就是干這個事情的,下面我們就實現一下v-model的功能

<div id="app"><input v-model="name" />
</div>
<script>let data = {name: '小蘭同學',age: 18,height: 170}// 遍歷每一個屬性Object.keys(data).forEach((key) => {// key 屬性名// data[key] 屬性值// data 原對象defineReactive(data, key, data[key])})function defineReactive(data, key, value) {Object.defineProperty(data, key, {get() {return value},set(newVal) {// 數據發生變化,操作dom進行更新if (newVal === value) {return}value = newValcompile()}})}// 編譯函數function compile() {let app = document.getElementById('app')// 1.拿到app下所有的子元素const nodes = app.childNodes   //  [text, input, text]//2.遍歷所有的子元素nodes.forEach(node => {// nodeType為1為元素節點if (node.nodeType === 1) {const attrs = node.attributes// 遍歷所有的attrubites找到 v-modelArray.from(attrs).forEach(attr => {const dirName = attr.nodeNameconst dataProp = attr.nodeValueif (dirName === 'v-model') {node.value = data[dataProp]// 視圖變化反應到數據 無非是事件監聽反向修改node.addEventListener('input', (e) => {data[dataProp] = e.target.value})}})}})}// 首次渲染compile()
</script>

現存的問題

無法做到精準更新

<div id="app"><p v-text="name"></p><p v-text="age"></p><p v-text="name"></p>
</div>
<script>let data = {name: '小蘭同學',age: 18,height: 180}// 遍歷每一個屬性Object.keys(data).forEach((key) => {// key 屬性名// data[key] 屬性值// data 原對象defineReactive(data, key, data[key])})function defineReactive(data, key, value) {Object.defineProperty(data, key, {get() {return value},set(newVal) {// 數據發生變化,操作dom進行更新if (newVal === value) {return}value = newValcompile()}})}// 編譯函數function compile() {let app = document.getElementById('app')// 1.拿到app下所有的子元素const nodes = app.childNodes   //  [text, input, text]//2.遍歷所有的子元素nodes.forEach(node => {// nodeType為1為元素節點if (node.nodeType === 1) {const attrs = node.attributesArray.from(attrs).forEach(attr => {const dirName = attr.nodeNameconst dataProp = attr.nodeValueconsole.log( dirName,dataProp)if (dirName === 'v-text') {console.log(`更新了${dirName}指令,需要更新的屬性為${dataProp}`)node.innerText = data[dataProp]}})}})}// 首次渲染compile()
</script>

下節中對本問題進行修復

寫在最后

?原創不易,還希望各位大佬支持一下\textcolor{blue}{原創不易,還希望各位大佬支持一下}

👍 點贊,你的認可是我創作的動力!\textcolor{green}{點贊,你的認可是我創作的動力!}

?? 收藏,你的青睞是我努力的方向!\textcolor{green}{收藏,你的青睞是我努力的方向!}

?? 評論,你的意見是我進步的財富!\textcolor{green}{評論,你的意見是我進步的財富!}

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/248472.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/248472.shtml
英文地址,請注明出處:http://en.pswp.cn/news/248472.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

【BZOJ3894】文理分科

已經連續很久沒有當場想出來題了。。。。 $yyb$認為這是一道傻逼題&#xff0c;但是我并不這么認為。。。。 題面 https://www.lydsy.com/JudgeOnline/problem.php?id3894 題解 加點&#xff1a;三叉戟結構的小技巧。 假設割$S$表示不學文&#xff0c;割$T$表示不學理。 對于一…

CodeForces 1131G. Most Dangerous Shark

題目簡述&#xff1a;從左到右依次有$n \leq 10^7$個Domino骨牌&#xff0c;高度為$h_i$&#xff0c;手動推倒他的花費為$c_i$。每個骨牌之間的距離為$1$。一個骨牌可以被向左或者向右推倒。當第$i$個骨牌被推倒時&#xff0c;他會以相同方向推倒與其距離$<h_i$的所有骨牌。…

大廠直通車【C認證】踵磅來襲

歡迎各位小伙伴們&#xff01; 首先為大家推薦一款刷題神奇哦 點擊鏈接訪問牛客網 各大互聯網大廠面試真題。從基礎到入階乃至原理刨析類面試題 應有盡有&#xff0c;趕快來裝備自己吧&#xff01;助你面試穩操勝券&#xff0c;solo全場面試官 你還在以為CSDN僅僅是一個簡簡單單…

理解JavaScript中的原型繼承(2)

兩年前在我學習JavaScript的時候我就寫過兩篇關于原型繼承的博客&#xff1a; 理解JavaScript中原型繼承 JavaScript中的原型繼承 這兩篇博客講的都是原型的使用&#xff0c;其中一篇還有我學習時的錯誤理解。今天看《Understanding Scopes》這讓我從新思考了一下原型繼承&…

深入Vue原理_全面剖析發布訂閱模式

文章目錄發布訂閱模式優化優化思路思考理解發布訂閱模式(自定義事件)收集更新函數觸發更新函數6.5 總結總結寫在最后本期推薦歡迎各位小伙伴們&#xff01; 為大家推薦一款刷題神奇哦 點擊鏈接訪問牛客網 各大互聯網大廠面試真題。從基礎到入階乃至原理刨析類面試題 應有盡有&a…

前端面試系列-JS 異步編程

并發與并行的區別&#xff1f; 并發是宏觀概念&#xff0c;我分別有任務 A 和任務 B&#xff0c;在一段時間內通過任務間的切換完成了這兩個任務&#xff0c;這種情況就可以稱之為并發。并行是微觀概念&#xff0c;假設 CPU 中存在兩個核心&#xff0c;那么我就可以同時完成任務…

web前端發展歷程

總覽前端發展史前言瀏覽器的發展史走進前端HTMLCSSjavaScript小前端時代大前端時代寫在最后前言 目前在IT公司中前端的崗位越來越成為不可或缺的&#xff0c;前端的地位也愈見明顯&#xff0c;很多學校已經體系的傳授前端課程&#xff0c;眾多培訓機構也將前端知識作為了主流課…

修改wordpress上傳文件大小限制

1. 登陸wordpress使用的數據庫&#xff0c;切換到使用的database 2. 操作如下&#xff1a; > select meta_key from wp_sitemeta; > select meta_key,meta_value from wp_sitemeta where meta_keyfileupload_maxk; 修改為20M: > update wp_sitemeta set meta_value204…

php的符號的排序大小

轉載于:https://www.cnblogs.com/cjjjj/p/10433334.html

淺談 HTTP 和 HTTPS

很多前端伙伴問題有沒有體系的面試題&#xff1f; 今天為大家推薦一款刷題神奇哦 點擊鏈接訪問牛客網 各大互聯網大廠面試真題。從基礎到入階乃至原理刨析類面試題 應有盡有&#xff0c;趕快來裝備自己吧&#xff01;助你面試穩操勝券&#xff0c;solo全場面試官 淺談 HTTP 和 …

Ubuntu 搭建 GitLab 筆記 ***

簡介 GitLab 社區版可以提供許多與 GitHub 相同的功能&#xff0c;且部署在屬于自己的機器上&#xff0c;我們會因為網絡及其他一些問題而不便使用 GitHub &#xff0c;這時部署一個 GitLab 是最好的選擇。 下載 GitLab 并安裝 我的環境是 Ubuntu 16.04 下進行部署操作。 GitLa…

在瀏覽器輸入URL到頁面展示發生了什么?

輸入URL后查詢緩存DNS服務器TCP三次握手HTTP協議包瀏覽器處理HTML文檔TCP 和 UDP 的區別寫在最后很多前端伙伴問題有沒有體系的面試題&#xff1f; 今天為大家推薦一款刷題神奇哦 點擊鏈接訪問牛客網 各大互聯網大廠面試真題。從基礎到入階乃至原理刨析類面試題 應有盡有&#…

iOS 高級去水印,涂鴉去水印

目前在研究一下圖像的處理&#xff0c;看了一下相關的軟件&#xff0c;比如&#xff1a;《去水印大師》&#xff0c;究竟去水印是怎么處理的呢&#xff1f;看圖分析。 一共是三個功能&#xff1a;快速去水印、高級去水印、涂鴉去水印 快速去水印&#xff1a;暫時沒找到好的處理…

Failed to execute goal maven-gpg-plugin 1.5 Sign

問題描述&#xff1a; 解決辦法&#xff1a;跳過maven-gpg-plugin <build> <pluginManagement><plugins><plugin><groupId>org.apache.maven.plugins</groupId><artifactId>maven-gpg-plugin</artifactId><configuration&g…

打造硬核敲門磚——簡歷

文章目錄 前言打造簡歷篇幅模板個人信息專業技能工作經歷項目經歷教育經歷個人總結簡歷格式寫在最后前言 作為高校的學生,你是否已經開始設想你以后的工作?作為職場的員工,你是否已經準備更換下一份工作了?不論你現在是什么身份、處于什么階段,這篇文章都能夠幫到你,只要…

Robot Framework 內置變量

Robot Framework 內置變量 轉自&#xff1a;https://blog.csdn.net/qq_26886929/article/details/53907755 Robot Framework 內部提供了一下直接可用的內置變量 1. 操作系統相關變量 內置的操作系統相關的變量&#xff0c;減少了測試數據對操作系統之間的差異性的關注 RF 中可用…

一文搞懂this指向

前言 那你說一下 js 中的 this 指向吧&#xff01;這句話已經成為面試官口中的高頻面試題&#xff0c;作為前端開發的我們&#xff0c;你真的搞懂了 this 指向了嗎&#xff1f;快來跟我一起來查漏補缺吧&#xff01;通過幾個小案例讓大家更能直白的理解 this 指向。 很多前端伙…

難怪大家丟掉了postman而選擇 Apifox

前言 當下采用前后端分離模式開發Web應用已經成為氣候&#xff0c;在開發階段有一個不成文的規定則是 項目開發后端先行 但是作為前端開發工程師的我們&#xff0c;難道在搭建完頁面后只能等待后端的接口么&#xff1f;這樣的話我們則完全被后端開發限制住了。在前面跟大家介紹…

mvc 模式和mtc 模式的區別

首先說說Web服務器開發領域里著名的MVC模式&#xff0c;所謂MVC就是把Web應用分為模型(M)&#xff0c;控制器(C)和視圖(V)三層&#xff0c;他們之間以一種插件式的、松耦合的方式連接在一起&#xff0c;模型負責業務對象與數據庫的映射(ORM)&#xff0c;視圖負責與用戶的交互(頁…

HP LaserJet MFP M227_M231雙面打印

雙面打印設置 轉載于:https://www.cnblogs.com/xiexiaokui/p/9261577.html