<ruby id="bdb3f"></ruby>

    <p id="bdb3f"><cite id="bdb3f"></cite></p>

      <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
        <p id="bdb3f"><cite id="bdb3f"></cite></p>

          <pre id="bdb3f"></pre>
          <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

          <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
          <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

          <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                <ruby id="bdb3f"></ruby>

                合規國際互聯網加速 OSASE為企業客戶提供高速穩定SD-WAN國際加速解決方案。 廣告
                [TOC] >[success] # ref,reactive 響應式引用的用法和原理 **ref** 與 **reactive** 是 **vue3** 提供給我們 **解決數據響應式問題的方法**,下面我們將通過 **2** 個例子來講解 **ref** 與 **reactive** 以及 **readonly** 、**toRefs** 具體用法。 1. **ref** :解決 **基本數據類型數據(基本類型:Boolean、String等等)** 的 **數據響應式問題** 2. **reactive** :解決 **非基本數據類型數據(引用類型:Array、Object等等)** 的 **數據響應式問題** 3. **readonly** :數據 **只讀** 。 4. **toRefs** : 解決 **解構賦值** 的 **數據響應式問題**。 >[success] ## ref **需求** :我們在 **setup** 中定義了變量 **name** , 并且將 **name** 返回 **return** 出去,在頁面的 **template 模板** 中使用 **name**, **2s 之后更改了變量 name** , 我們 **希望 template 模板上的 name 也隨之更新** , 代碼如下: 1. **非響應式數據案例** **index.html** ~~~ <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>ref 響應式引用的用法和原理</title> <!-- 通過cdn方式引入vue --> <script src="https://unpkg.com/vue@next"></script> </head> <body> <div id="root"></div> </body> <script> const app = Vue.createApp({ template: ` <div>{{name}}</div> `, /** * created 實例被完全初始化之前 * @param {object} props - 當前組件的props * @param {number} contex - 上下文 */ setup(props, contex) { // 聲明定義變量name let name = 'dell' // 2s 后更改 name setTimeout(() => { name = 'lee' }, 2000); return { name // data中的變量 } } }) const vm = app.mount('#root') </script> </html> ~~~ 2. **ref 響應式數據案例** 上面的數據,無法更新,這是 **因為 name 只是一個普通的變量并不會響應式的更新** ,如果想 **響應式的更新 name** ,使用 **ref** 可以解決 **基本數據類型數據** 的 **數據響應式問題** 。 **index.html** ~~~ <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>ref 響應式引用的用法和原理</title> <!-- 通過cdn方式引入vue --> <script src="https://unpkg.com/vue@next"></script> </head> <body> <div id="root"></div> </body> <script> // ref 響應式的引用 // 原理, 通過 proxy 對數據進行封裝, 當數據變化時, 觸發模板等內容的更新 // ref 處理基礎類型的數據 const app = Vue.createApp({ template: ` <div>{{name}}</div> `, /** * created 實例被完全初始化之前 * @param {object} props - 當前組件的props * @param {number} contex - 上下文 */ setup(props, contex) { // 引入 composition API 的 ref const { ref } = Vue // 調用 ref 后,proxy, 'dell' 變成 proxy({value: 'dell'}) 這樣的一個響應式引用 let name = ref('dell') // 值會存入到 name.value 中 // 2s 后更改 name setTimeout(() => { name.value = 'lee' // 修改 name.value 的值 }, 2000); return { name // data中的變量 } } }) const vm = app.mount('#root') </script> </html> ~~~ **template 模板** 中不需要寫 **name.value** ,直接寫 **name** 就行,因為 **vue** 在 **做模板處理時,它會做一個轉換,它如果知道 name 是通過 ref 返回的一個響應式引用,會自動的在底層幫我們調用 name.value** >[success] ## reactive 下面的代碼是 **非基本數據類型數據** 的案例,也是 **無法做到數據的響應式** 。 1. **非響應式數據案例** **index.html** ~~~ <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>reactive 響應式引用的用法和原理</title> <!-- 通過cdn方式引入vue --> <script src="https://unpkg.com/vue@next"></script> </head> <body> <div id="root"></div> </body> <script> const app = Vue.createApp({ template: ` <div>{{nameObj.name}}</div> `, /** * created 實例被完全初始化之前 * @param {object} props - 當前組件的props * @param {number} contex - 上下文 */ setup(props, contex) { // 定義聲明對象 const nameObj = { name: 'dell' } // 2s 后更改 nameObj setTimeout(() => { nameObj.name = 'lee' }, 2000); return { nameObj // data中的變量 } } }) const vm = app.mount('#root') </script> </html> ~~~ 2. **reactive 響應式數據案例** **reactive** 可以解決 **非基本數據類型數據** 的 **數據響應式問題** 。 **index.html** ~~~ <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>reactive 響應式引用的用法和原理</title> <!-- 通過cdn方式引入vue --> <script src="https://unpkg.com/vue@next"></script> </head> <body> <div id="root"></div> </body> <script> // reactive 響應式的引用 // 原理, 通過 proxy 對數據進行封裝, 當數據變化時, 觸發模板等內容的更新 // reactive 處理非基礎類型的數據 const app = Vue.createApp({ template: ` <div>{{nameObj.name}}</div> `, /** * created 實例被完全初始化之前 * @param {object} props - 當前組件的props * @param {number} contex - 上下文 */ setup(props, contex) { // 引入 composition API 的 reactive const { reactive } = Vue // 調用 reactive 后,proxy, { name: 'dell' } 變成 proxy({ name: 'dell' }) 這樣的一個響應式引用 const nameObj = reactive({ name: 'dell' }) // 2s 后更改 nameObj setTimeout(() => { nameObj.name = 'lee' }, 2000); return { nameObj // data中的變量 } } }) const vm = app.mount('#root') </script> </html> ~~~ 上面是數據是 **對象** ,也可以使用 **數組** ,如下: ~~~ <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>reactive 響應式引用的用法和原理</title> <!-- 通過cdn方式引入vue --> <script src="https://unpkg.com/vue@next"></script> </head> <body> <div id="root"></div> </body> <script> // reactive 響應式的引用 // 原理, 通過 proxy 對數據進行封裝, 當數據變化時, 觸發模板等內容的更新 // reactive 處理非基礎類型的數據 const app = Vue.createApp({ template: ` <div>{{nameObj[0]}}</div> `, /** * created 實例被完全初始化之前 * @param {object} props - 當前組件的props * @param {number} contex - 上下文 */ setup(props, contex) { // 引入 composition API 的 reactive const { reactive } = Vue const nameObj = reactive([123]) // 2s 后更改 nameObj setTimeout(() => { nameObj[0] = 456 }, 2000); return { nameObj // data中的變量 } } }) const vm = app.mount('#root') </script> </html> ~~~ >[success] ## readonly 假如我想讓部分數據 **不希望,數據被變更** ,變成 **只讀狀態** , 我們可以使用 **vue3** 提供的 **readonly** 實現這個功能,代碼如下: **index.html** ~~~ <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>readonly 的用法和原理</title> <!-- 通過cdn方式引入vue --> <script src="https://unpkg.com/vue@next"></script> </head> <body> <div id="root"></div> </body> <script> // ref, reactive 響應式的引用 // 原理, 通過 proxy 對數據進行封裝, 當數據變化時, 觸發模板等內容的更新 // reactive 處理非基礎類型的數據 const app = Vue.createApp({ template: ` <div>{{nameObj[0]}}</div> `, /** * created 實例被完全初始化之前 * @param {object} props - 當前組件的props * @param {number} contex - 上下文 */ setup(props, contex) { // 引入 composition API 的 reactive const { reactive, readonly } = Vue const nameObj = reactive([123]) // 復制一份數據 const copyNameObj = readonly(nameObj) // 2s 后更改 nameObj 與copyNameObj setTimeout(() => { nameObj[0] = 456 copyNameObj[0] = 456 }, 2000); return { nameObj, // data中的變量 copyNameObj } } }) const vm = app.mount('#root') </script> </html> ~~~ 這樣 **2s** 過后,瀏覽器控制臺就會 **拋出警告** 。 >[success] ## toRefs 下面代碼中在 **setup 函數** 中 **return** 一個對象 **index.html** ~~~ <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>toRefs 的用法和原理</title> <!-- 通過cdn方式引入vue --> <script src="https://unpkg.com/vue@next"></script> </head> <body> <div id="root"></div> </body> <script> const app = Vue.createApp({ template: ` <div>{{nameObj.name}}</div> `, /** * created 實例被完全初始化之前 * @param {object} props - 當前組件的props * @param {number} contex - 上下文 */ setup(props, contex) { // 引入 composition API 的 reactive const { reactive } = Vue // 調用 reactive 后,proxy, { name: 'dell' } 變成 proxy({ name: 'dell' }) 這樣的一個響應式引用 const nameObj = reactive({ name: 'dell' }) // 2s 后更改 nameObj setTimeout(() => { nameObj.name = 'lee' }, 2000); return { nameObj // data中的變量 } } }) const vm = app.mount('#root') </script> </html> ~~~ 有些人就會覺得這么寫很麻煩,用 **ES6 解構賦值** 直接 **return** 一個 **name** ,像下面這樣寫: ~~~ <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>toRefs 的用法和原理</title> <!-- 通過cdn方式引入vue --> <script src="https://unpkg.com/vue@next"></script> </head> <body> <div id="root"></div> </body> <script> const app = Vue.createApp({ template: ` <div>{{name}}</div> `, /** * created 實例被完全初始化之前 * @param {object} props - 當前組件的props * @param {number} contex - 上下文 */ setup(props, contex) { // 引入 composition API 的 reactive const { reactive } = Vue // 調用 reactive 后,proxy, { name: 'dell' } 變成 proxy({ name: 'dell' }) 這樣的一個響應式引用 const nameObj = reactive({ name: 'dell' }) // 2s 后更改 nameObj setTimeout(() => { nameObj.name = 'lee' }, 2000); // 解構賦值 const { name } = nameObj // data中的變量 return { name } } }) const vm = app.mount('#root') </script> </html> ~~~ **2s 后就會發現不生效** , **解構賦值** 并沒有生效,因為 **解構只是把這個值導出去,這個值并不是響應式的** ,如果想做**解構賦值** ,解決這個問題,需要使用 **toRefs** 才可以解決這個問題,代碼如下: ~~~ <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>toRefs 的用法和原理</title> <!-- 通過cdn方式引入vue --> <script src="https://unpkg.com/vue@next"></script> </head> <body> <div id="root"></div> </body> <script> const app = Vue.createApp({ template: ` <div>{{name}}</div> `, /** * created 實例被完全初始化之前 * @param {object} props - 當前組件的props * @param {number} contex - 上下文 */ setup(props, contex) { // 引入 composition API 的 reactive const { reactive, toRefs } = Vue // 調用 reactive 后,proxy, { name: 'dell' } 變成 proxy({ name: 'dell' }) 這樣的一個響應式引用 const nameObj = reactive({ name: 'dell' }) // 2s 后更改 nameObj setTimeout(() => { nameObj.name = 'lee' }, 2000); // 解構賦值 // 調用 toRefs 后,它會把 proxy({ name: 'dell' }) 轉換成 { name: proxy({value:'dell'}) } // 實際上最終返回的是 { name: proxy({value:'dell'}) } const { name } = toRefs(nameObj) // data中的變量 return { name } } }) const vm = app.mount('#root') </script> </html> ~~~ >[success] ## 總結 當我們學了 **ref** 、 **reactive** 這種新的 **composition API** 之后,我們完全 **可以替代老的語法中 data 這種寫法**,比如說以前 **定義** 都在 **data 中定義變量** ,如下: ~~~ data() { return { name: 'dell', nameObj: { name: 'dell' } } } ~~~ 用新的 **composition API 語法來定義的話,完全沒必要用 data** ,用 **ref** 、 **reactive** 這種形式來寫即可。
                  <ruby id="bdb3f"></ruby>

                  <p id="bdb3f"><cite id="bdb3f"></cite></p>

                    <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
                      <p id="bdb3f"><cite id="bdb3f"></cite></p>

                        <pre id="bdb3f"></pre>
                        <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

                        <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
                        <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

                        <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                              <ruby id="bdb3f"></ruby>

                              哎呀哎呀视频在线观看