欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

Vue3 的響應(yīng)式和以前有什么區(qū)別,Proxy 無(wú)敵?

 更新時(shí)間:2020年05月20日 11:53:58   作者:sam9831  
這篇文章主要介紹了Vue3 的響應(yīng)式和以前有什么區(qū)別,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧

前言

大家都知道,Vue2 里的響應(yīng)式其實(shí)有點(diǎn)像是一個(gè)半完全體,對(duì)于對(duì)象上新增的屬性無(wú)能為力,對(duì)于數(shù)組則需要攔截它的原型方法來(lái)實(shí)現(xiàn)響應(yīng)式。

舉個(gè)例子:

let vm = new Vue({
 data() {
 return {
 a: 1
 }
 }
})

// ❌ oops,沒(méi)反應(yīng)!
vm.b = 2 
let vm = new Vue({
 data() {
 return {
 a: 1
 }
 },
 watch: {
 b() {
 console.log('change !!')
 }
 }
})

// ❌ oops,沒(méi)反應(yīng)!
vm.b = 2

這種時(shí)候,Vue 提供了一個(gè) api:this.$set,來(lái)使得新增的屬性也擁有響應(yīng)式的效果。

但是對(duì)于很多新手來(lái)說(shuō),很多時(shí)候需要小心翼翼的去判斷到底什么情況下需要用 $set,什么時(shí)候可以直接觸發(fā)響應(yīng)式。
總之,在 Vue3 中,這些都將成為過(guò)去。本篇文章會(huì)帶你仔細(xì)講解,proxy 到底會(huì)給 Vue3 帶來(lái)怎么樣的便利。并且會(huì)從源碼級(jí)別,告訴你這些都是如何實(shí)現(xiàn)的。

響應(yīng)式倉(cāng)庫(kù)

Vue3 不同于 Vue2 也體現(xiàn)在源碼結(jié)構(gòu)上,Vue3 把耦合性比較低的包分散在 packages 目錄下單獨(dú)發(fā)布成 npm 包。 這也是目前很流行的一種大型項(xiàng)目管理方式 Monorepo。

其中負(fù)責(zé)響應(yīng)式部分的倉(cāng)庫(kù)就是 @vue/rectivity,它不涉及 Vue 的其他的任何部分,是非常非常 「正交」 的一種實(shí)現(xiàn)方式。

甚至可以輕松的集成進(jìn) React。

這也使得本篇的分析可以更加聚焦的分析這一個(gè)倉(cāng)庫(kù),排除其他無(wú)關(guān)部分。

區(qū)別

Proxy 和 Object.defineProperty 的使用方法看似很相似,其實(shí) Proxy 是在 「更高維度」 上去攔截屬性的修改的,怎么理解呢?

Vue2 中,對(duì)于給定的 data,如 { count: 1 },是需要根據(jù)具體的 key 也就是 count,去對(duì)「修改 data.count 」 和 「讀取 data.count」進(jìn)行攔截,也就是

Object.defineProperty(data, 'count', {
 get() {},
 set() {},
})

必須預(yù)先知道要攔截的 key 是什么,這也就是為什么 Vue2 里對(duì)于對(duì)象上的新增屬性無(wú)能為力。
而 Vue3 所使用的 Proxy,則是這樣攔截的:

new Proxy(data, {
 get(key) { },
 set(key, value) { },
})

可以看到,根本不需要關(guān)心具體的 key,它去攔截的是 「修改 data 上的任意 key」 和 「讀取 data 上的任意 key」。
所以,不管是已有的 key  還是新增的 key,都逃不過(guò)它的魔爪。

但是 Proxy 更加強(qiáng)大的地方還在于 Proxy 除了 get 和 set,還可以攔截更多的操作符。

簡(jiǎn)單的例子🌰

先寫一個(gè) Vue3 響應(yīng)式的最小案例,本文的相關(guān)案例都只會(huì)用 reactive 和 effect 這兩個(gè) api。如果你了解過(guò) React 中的 useEffect,相信你會(huì)對(duì)這個(gè)概念秒懂,Vue3 的 effect 不過(guò)就是去掉了手動(dòng)聲明依賴的「進(jìn)化版」的 useEffect。
React 中手動(dòng)聲明 [data.count] 這個(gè)依賴的步驟被 Vue3 內(nèi)部直接做掉了,在 effect 函數(shù)內(nèi)部讀取到 data.count 的時(shí)候,它就已經(jīng)被收集作為依賴了。
Vue3:

// 響應(yīng)式數(shù)據(jù)
const data = reactive({ 
 count: 1
})

// 觀測(cè)變化
effect(() => console.log('count changed', data.count))

// 觸發(fā) console.log('count changed', data.count) 重新執(zhí)行
data.count = 2

React:

// 數(shù)據(jù)
const [data, setData] = useState({
 count: 1
})

// 觀測(cè)變化 需要手動(dòng)聲明依賴
useEffect(() => {
 console.log('count changed', data.count)
}, [data.count])

// 觸發(fā) console.log('count changed', data.count) 重新執(zhí)行
setData({
 count: 2
})

其實(shí)看到這個(gè)案例,聰明的你也可以把 effect 中的回調(diào)函數(shù)聯(lián)想到視圖的重新渲染、 watch 的回調(diào)函數(shù)等等…… 它們是同樣基于這套響應(yīng)式機(jī)制的。

而本文的核心目的,就是探究這個(gè)基于 Proxy 的 reactive api,到底能強(qiáng)大到什么程度,能監(jiān)聽到用戶對(duì)于什么程度的修改。

先講講原理

先最小化的講解一下響應(yīng)式的原理,其實(shí)就是在 Proxy 第二個(gè)參數(shù) handler 也就是陷阱操作符中,攔截各種取值、賦值操作,依托 track 和 trigger 兩個(gè)函數(shù)進(jìn)行依賴收集和派發(fā)更新。

  • track 用來(lái)在讀取時(shí)收集依賴。
  • trigger 用來(lái)在更新時(shí)觸發(fā)依賴。

track

function track(target: object, type: TrackOpTypes, key: unknown) {
 const depsMap = targetMap.get(target);
 // 收集依賴時(shí) 通過(guò) key 建立一個(gè) set
 let dep = new Set()
 targetMap.set(ITERATE_KEY, dep)
 // 這個(gè) effect 可以先理解為更新函數(shù) 存放在 dep 里
 dep.add(effect) 
}

target 是原對(duì)象。
type 是本次收集的類型,也就是收集依賴的時(shí)候用來(lái)標(biāo)識(shí)是什么類型的操作,比如上文依賴中的類型就是 get,這個(gè)后續(xù)會(huì)詳細(xì)講解。
key 是指本次訪問(wèn)的是數(shù)據(jù)中的哪個(gè) key,比如上文例子中收集依賴的 key 就是 count
首先全局會(huì)存在一個(gè) targetMap,它用來(lái)建立 數(shù)據(jù) -> 依賴 的映射,它是一個(gè) WeakMap 數(shù)據(jù)結(jié)構(gòu)。
而 targetMap 通過(guò)數(shù)據(jù) target,可以獲取到 depsMap,它用來(lái)存放這個(gè)數(shù)據(jù)對(duì)應(yīng)的所有響應(yīng)式依賴。
depsMap 的每一項(xiàng)則是一個(gè) Set 數(shù)據(jù)結(jié)構(gòu),而這個(gè) Set 就存放著對(duì)應(yīng) key 的更新函數(shù)。
是不是有點(diǎn)繞?我們用一個(gè)具體的例子來(lái)舉例吧。

const target = { count: 1}
const data = reactive(target)

const effection = effect(() => {
 console.log(data.count)
})

對(duì)于這個(gè)例子的依賴關(guān)系,

全局的 targetMap 是:

targetMap: {
 { count: 1 }: dep 
}

dep 則是

dep: {
 count: Set { effection }
}

這樣一層層的下去,就可以通過(guò) target 找到 count 對(duì)應(yīng)的更新函數(shù) effection 了。

trigger

這里是最小化的實(shí)現(xiàn),僅僅為了便于理解原理,實(shí)際上要復(fù)雜很多,

其實(shí) type 的作用很關(guān)鍵,先記住,后面會(huì)詳細(xì)講。

export function trigger(
 target: object,
 type: TriggerOpTypes,
 key?: unknown,
) {
 // 簡(jiǎn)化來(lái)說(shuō) 就是通過(guò) key 找到所有更新函數(shù) 依次執(zhí)行
 const dep = targetMap.get(target)
 dep.get(key).forEach(effect => effect())
}

新增屬性

這個(gè)上文已經(jīng)講了,由于 Proxy 完全不關(guān)心具體的 key,所以沒(méi)問(wèn)題。

// 響應(yīng)式數(shù)據(jù)
const data = reactive({ 
 count: 1
})

// 觀測(cè)變化
effect(() => console.log('newCount changed', data.newCount))

// ✅ 觸發(fā)響應(yīng)
data.newCount = 2

數(shù)組新增索引:

// 響應(yīng)式數(shù)據(jù)
const data = reactive([])

// 觀測(cè)變化
effect(() => console.log('data[1] changed', data[1]))

// ✅ 觸發(fā)響應(yīng)
data[1] = 5

數(shù)組調(diào)用原生方法:

const data = reactive([])
effect(() => console.log('c', data[1]))

// 沒(méi)反應(yīng)
data.push(1)

// ✅ 觸發(fā)響應(yīng) 因?yàn)樾薷牧讼聵?biāo)為 1 的值
data.push(2)

其實(shí)這一個(gè)案例就比較有意思了,我們僅僅是在調(diào)用 push,但是等到數(shù)組的第二項(xiàng)被 push的時(shí)候,我們之前關(guān)注 data[1] 為依賴的回調(diào)函數(shù)也執(zhí)行了,這是什么原理呢?寫個(gè)簡(jiǎn)單的 Proxy 就知道了。

const raw = []
const arr = new Proxy(raw, {
 get(target, key) {
 console.log('get', key)
 return Reflect.get(target, key)
 },
 set(target, key, value) {
 console.log('set', key)
 return Reflect.set(target, key, value)
 }
})

arr.push(1)

在這個(gè)案例中,我們只是打印出了對(duì)于 raw 這個(gè)數(shù)組上的所有 get、set 操作,并且調(diào)用 Reflect 這個(gè) api 原樣處理取值和賦值操作后返回??纯?arr.push(1) 后控制臺(tái)打印出了什么?

get push
get length
set 0
set length

原來(lái)一個(gè)小小的 push,會(huì)觸發(fā)兩對(duì) get 和 set,我們來(lái)想象一下流程:

  • 讀取 push 方法
  • 讀取 arr 原有的 length 屬性
  • 對(duì)于數(shù)組第 0 項(xiàng)賦值
  • 對(duì)于 length 屬性賦值

這里的重點(diǎn)是第三步,對(duì)于第 index 項(xiàng)的賦值,那么下次再 push,可以想象也就是對(duì)于第 1 項(xiàng)觸發(fā) set 操作。
而我們?cè)诶又凶x取 data[1],是一定會(huì)把對(duì)于 1 這個(gè)下標(biāo)的依賴收集起來(lái)的,這也就清楚的解釋了為什么 push 的時(shí)候

也能精準(zhǔn)的觸發(fā)響應(yīng)式依賴的執(zhí)行。

對(duì)了,記住這個(gè)對(duì)于 length 的 set 操作,后面也會(huì)用到,很重要。

遍歷后新增

// 響應(yīng)式數(shù)據(jù)
const data = reactive([])

// 觀測(cè)變化
effect(() => console.log('data map +1', data.map(item => item + 1))

// ✅ 觸發(fā)響應(yīng) 打印出 [2]
data.push(1)

這個(gè)攔截很神奇,但是也很合理,轉(zhuǎn)化成現(xiàn)實(shí)里的一個(gè)例子來(lái)看,

假設(shè)我們要根據(jù)學(xué)生 id 的集合 ids, 去請(qǐng)求學(xué)生詳細(xì)信息,那么僅僅是需要這樣寫即可:

const state = reactive({})
const ids = reactive([1])

effect(async () => {
 state.students = await axios.get('students/batch', ids.map(id => ({ id })))
})

// ✅ 觸發(fā)響應(yīng) 
ids.push(2)

這樣,每次調(diào)用各種 api 改變 ids 數(shù)組,都會(huì)重新發(fā)送請(qǐng)求獲取最新的學(xué)生列表。

如果我在監(jiān)聽函數(shù)中調(diào)用了 map、forEach 等 api,

說(shuō)明我關(guān)心這個(gè)數(shù)組的長(zhǎng)度變化,那么 push 的時(shí)候觸發(fā)響應(yīng)是完全正確的。

但是它是如何實(shí)現(xiàn)的呢?感覺(jué)似乎很復(fù)雜啊。

因?yàn)?effect 第一次執(zhí)行的時(shí)候, data 還是個(gè)空數(shù)組,怎么會(huì) push 的時(shí)候能觸發(fā)更新呢?

還是用剛剛的小測(cè)試,看看 map 的時(shí)候會(huì)發(fā)生什么事情。

const raw = [1, 2]
const arr = new Proxy(raw, {
 get(target, key) {
 console.log('get', key)
 return Reflect.get(target, key)
 },
 set(target, key, value) {
 console.log('set', key)
 return Reflect.set(target, key, value)
 }
})

arr.map(v => v + 1)
get map
get length
get constructor
get 0
get 1

和 push 的部分有什么相同的?找一下線索,我們發(fā)現(xiàn) map 的時(shí)候會(huì)觸發(fā) get length,而在觸發(fā)更新的時(shí)候, Vue3 內(nèi)部會(huì)對(duì) 「新增 key」 的操作進(jìn)行特殊處理,這里是新增了 0 這個(gè)下標(biāo)的值,會(huì)走到 trigger  中這樣的一段邏輯里去:

源碼地址

// 簡(jiǎn)化版
if (isAddOrDelete) {
 add(depsMap.get('length'))
}

把之前讀取 length 時(shí)收集到的依賴拿到,然后觸發(fā)函數(shù)。
這就一目了然了,我們?cè)?effect 里 map 操作讀取了 length,收集了 length 的依賴。
在新增 key 的時(shí)候, 觸發(fā) length 收集到的依賴,觸發(fā)回調(diào)函數(shù)即可。
對(duì)了,對(duì)于 for of 操作,也一樣可行:

// 響應(yīng)式數(shù)據(jù)
const data = reactive([])

// 觀測(cè)變化
effect(() => {
 for (const val of data) {
 console.log('val', val)
 }
})

// ✅ 觸發(fā)響應(yīng) 打印出 val 1
data.push(1)

可以按我們剛剛的小試驗(yàn)自己跑一下攔截, for of 也會(huì)觸發(fā) length 的讀取。
length 真是個(gè)好同志…… 幫了大忙了。

遍歷后刪除或者清空

注意上面的源碼里的判斷條件是 isAddOrDelete,所以刪除的時(shí)候也是同理,借助了 length 上收集到的依賴。

// 簡(jiǎn)化版
if (isAddOrDelete) {
 add(depsMap.get('length'))
}
const arr = reactive([1])
 
effect(() => {
 console.log('arr', arr.map(v => v))
})

// ✅ 觸發(fā)響應(yīng) 
arr.length = 0

// ✅ 觸發(fā)響應(yīng) 
arr.splice(0, 1)

真的是什么操作都能響應(yīng),愛了愛了。

獲取 keys

const obj = reactive({ a: 1 })
 
effect(() => {
 console.log('keys', Reflect.ownKeys(obj))
})

effect(() => {
 console.log('keys', Object.keys(obj))
})

effect(() => {
 for (let key in obj) {
 console.log(key)
 }
})

// ✅ 觸發(fā)所有響應(yīng) 
obj.b = 2

這幾種獲取 key 的方式都能成功的攔截,其實(shí)這是因?yàn)?Vue 內(nèi)部攔截了 ownKeys 操作符。

const ITERATE_KEY = Symbol( 'iterate' );

function ownKeys(target) {
 track(target, "iterate", ITERATE_KEY);
 return Reflect.ownKeys(target);
}

ITERATE_KEY 就作為一個(gè)特殊的標(biāo)識(shí)符,表示這是讀取 key 的時(shí)候收集到的依賴。它會(huì)被作為依賴收集的 key。
那么在觸發(fā)更新時(shí),其實(shí)就對(duì)應(yīng)這段源碼:

if (isAddOrDelete) {
 add(depsMap.get(isArray(target) ? 'length' : ITERATE_KEY));
}

其實(shí)就是我們聊數(shù)組的時(shí)候,代碼簡(jiǎn)化掉的那部分。判斷非數(shù)組,則觸發(fā) ITERATE_KEY 對(duì)應(yīng)的依賴。

小彩蛋:

  • Reflect.ownKeys、 Object.keys 和 for in 其實(shí)行為是不同的,
  • Reflect.ownKeys 可以收集到 Symbol 類型的 key,不可枚舉的 key。

舉例來(lái)說(shuō):

var a = {
 [Symbol(2)]: 2,
}

Object.defineProperty(a, 'b', {
 enumerable: false,
})

Reflect.ownKeys(a) // [Symbol(2), 'b']
Object.keys(a) // []

回看剛剛提到的 ownKeys 攔截,

function ownKeys(target) {
 track(target, "iterate", ITERATE_KEY);
 // 這里直接返回 Reflect.ownKeys(target)
 return Reflect.ownKeys(target);
}

內(nèi)部直接之間返回了 Reflect.ownKeys(target),按理來(lái)說(shuō)這個(gè)時(shí)候 Object.keys 的操作經(jīng)過(guò)了這個(gè)攔截,也會(huì)按照 Reflect.ownKeys 的行為去返回值。

然而最后返回的結(jié)果卻還是 Object.keys 的結(jié)果,這是比較神奇的一點(diǎn)。

刪除對(duì)象屬性

有了上面 ownKeys 的基礎(chǔ),我們?cè)賮?lái)看看這個(gè)例子

const obj = reactive({ a: 1, b: 2})
 
effect(() => {
 console.log(Object.keys(obj))
})

// ✅ 觸發(fā)響應(yīng) 
delete obj['b']

這也是個(gè)神奇的操作,原理在于對(duì)于 deleteProperty 操作符的攔截:

function deleteProperty(target: object, key: string | symbol): boolean {
 const result = Reflect.deleteProperty(target, key)
 trigger(target, TriggerOpTypes.DELETE, key)
 return result
}

這里又用到了 TriggerOpTypes.DELETE 的類型,根據(jù)上面的經(jīng)驗(yàn),一定對(duì)它有一些特殊的處理。
其實(shí)還是 trigger 中的那段邏輯:

const isAddOrDelete = type === TriggerOpTypes.ADD || type === TriggerOpTypes.DELETE
if (isAddOrDelete) {
 add(depsMap.get(isArray(target) ? 'length' : ITERATE_KEY))
}

這里的 target 不是數(shù)組,所以還是會(huì)去觸發(fā) ITERATE_KEY 收集的依賴,也就是上面例子中剛提到的對(duì)于 key 的讀取收集到的依賴。

判斷屬性是否存在

const obj = reactive({})

effect(() => {
 console.log('has', Reflect.has(obj, 'a'))
})

effect(() => {
 console.log('has', 'a' in obj)
})

// ✅ 觸發(fā)兩次響應(yīng) 
obj.a = 1

這個(gè)就很簡(jiǎn)單了,就是利用了 has 操作符的攔截。

function has(target, key) {
 const result = Reflect.has(target, key);
 track(target, "has", key);
 return result;
}

性能

  1. 首先 Proxy 作為瀏覽器的新標(biāo)準(zhǔn),性能上是一定會(huì)得到廠商的大力優(yōu)化的,拭目以待。
  2. Vue3 對(duì)于響應(yīng)式數(shù)據(jù),不再像 Vue2 中那樣遞歸對(duì)所有的子數(shù)據(jù)進(jìn)行響應(yīng)式定義了,而是再獲取到深層數(shù)據(jù)的時(shí)候再去利用 reactive 進(jìn)一步定義響應(yīng)式,這對(duì)于大量數(shù)據(jù)的初始化場(chǎng)景來(lái)說(shuō)收益會(huì)非常大。

比如,對(duì)于

const obj = reactive({
 foo: {
 bar: 1
 }
})

初始化定義 reactive 的時(shí)候,只會(huì)對(duì) obj 淺層定義響應(yīng)式,而真正讀取到 obj.foo 的時(shí)候,才會(huì)對(duì) foo 這一層對(duì)象定義響應(yīng)式,簡(jiǎn)化源碼如下:

function get(target: object, key: string | symbol, receiver: object) {
 const res = Reflect.get(target, key, receiver)
 // 這段就是惰性定義
 return isObject(res)
 ? reactive(res)
 : res
}

推薦閱讀

其實(shí) Vue3 對(duì)于 Map 和 Set 這兩種數(shù)據(jù)類型也是完全支持響應(yīng)式的,對(duì)于它們的原型方法也都做了完善的攔截,限于篇幅原因本文不再贅述。

說(shuō)實(shí)話 Vue3 的響應(yīng)式部分代碼邏輯分支還是有點(diǎn)過(guò)多,對(duì)于代碼理解不是很友好,因?yàn)樗€會(huì)涉及到 readonly 等只讀化的操作,如果看完這篇文章你對(duì)于 Vue3 的響應(yīng)式原理非常感興趣的話,建議從簡(jiǎn)化版的庫(kù)入手去讀源碼。

這里我推薦observer-util,我解讀過(guò)這個(gè)庫(kù)的源碼,和 Vue3 的實(shí)現(xiàn)原理基本上是一模一樣!但是簡(jiǎn)單了很多。麻雀雖小,五臟俱全。里面的注釋也很齊全。

當(dāng)然,如果你的英文不是很熟練,也可以看我精心用 TypeScript + 中文注釋基于 observer-util 重寫的這套代碼:
typescript-proxy-reactive

對(duì)于這個(gè)庫(kù)的解讀,可以看我之前的兩篇文章:
帶你徹底搞懂Vue3的Proxy響應(yīng)式原理!TypeScript從零實(shí)現(xiàn)基于Proxy的響應(yīng)式庫(kù)。
帶你徹底搞懂Vue3的Proxy響應(yīng)式原理!基于函數(shù)劫持實(shí)現(xiàn)Map和Set的響應(yīng)式

在第二篇文章里,你也可以對(duì)于 Map 和 Set 可以做什么攔截操作,獲得源碼級(jí)別的理解。

總結(jié)

Vue3 的 Proxy 真的很強(qiáng)大,把 Vue2 里我認(rèn)為心智負(fù)擔(dān)很大的一部分給解決掉了。(在我剛上手 Vue 的時(shí)候,我是真的不知道什么情況下該用 $set),它的 composition-api 又可以完美對(duì)標(biāo) React Hook,并且得益于響應(yīng)式系統(tǒng)的強(qiáng)大,在某些方面是優(yōu)勝于它的。精讀《Vue3.0 Function API》

希望這篇文章能在 Vue3 正式到來(lái)之前,提前帶你熟悉 Vue3 的一些新特性。

擴(kuò)展閱讀

Proxy 的攔截器里有個(gè) receiver 參數(shù),在本文中為了簡(jiǎn)化沒(méi)有體現(xiàn)出來(lái),它是用來(lái)做什么的?國(guó)內(nèi)的網(wǎng)站比較少能找到這個(gè)資料:

new Proxy(raw, {
 get(target, key, receiver) {
 return Reflect.get(target, key, receiver)
 }
})

可以看 StackOverflow 上的問(wèn)答:what-is-a-receiver-in-javascript
也可以看我的總結(jié)
Proxy 和 Reflect 中的 receiver 到底是什么?

到此這篇關(guān)于Vue3 的響應(yīng)式和以前有什么區(qū)別,Proxy 無(wú)敵?的文章就介紹到這了,更多相關(guān)Vue3 響應(yīng)式內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家! 

相關(guān)文章

  • vue使用vue-json-viewer插件展示JSON格式數(shù)據(jù)的方法

    vue使用vue-json-viewer插件展示JSON格式數(shù)據(jù)的方法

    這篇文章主要給大家介紹了關(guān)于vue使用vue-json-viewer插件展示JSON格式數(shù)據(jù)的相關(guān)資料,前端使用這個(gè)插件可以方便展現(xiàn)出json格式的數(shù)據(jù),下載引入使用代碼可直接使用,需要的朋友可以參考下
    2024-05-05
  • vue-router的HTML5 History 模式設(shè)置

    vue-router的HTML5 History 模式設(shè)置

    這篇文章主要介紹了vue-router的HTML5 History模式設(shè)置,小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧
    2018-09-09
  • vue使用swiper實(shí)現(xiàn)中間大兩邊小的輪播圖效果

    vue使用swiper實(shí)現(xiàn)中間大兩邊小的輪播圖效果

    這篇文章主要介紹了vue使用swiper實(shí)現(xiàn)中間大兩邊小的輪播圖效果,本文分步驟通過(guò)實(shí)例代碼講解的非常詳細(xì),需要的朋友可以參考下
    2019-11-11
  • vue3在table里使用elementUI的form表單驗(yàn)證的示例代碼

    vue3在table里使用elementUI的form表單驗(yàn)證的示例代碼

    這篇文章主要介紹了vue3在table里使用elementUI的form表單驗(yàn)證的示例代碼,本文通過(guò)示例代碼給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下
    2023-12-12
  • element ui表格實(shí)現(xiàn)下拉篩選功能

    element ui表格實(shí)現(xiàn)下拉篩選功能

    這篇文章主要為大家詳細(xì)介紹了element ui表格實(shí)現(xiàn)下拉篩選功能,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2021-11-11
  • VUE中的自定義指令鉤子函數(shù)講解

    VUE中的自定義指令鉤子函數(shù)講解

    這篇文章主要介紹了VUE中的自定義指令鉤子函數(shù),具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2022-08-08
  • Vue 3中的異步操作管理示例分析

    Vue 3中的異步操作管理示例分析

    在現(xiàn)代Web應(yīng)用開發(fā)中,異步操作是常見的挑戰(zhàn),本文介紹了Vue3中管理多個(gè)異步操作的方法,幫助開發(fā)者提高編碼效率和應(yīng)用性能,感興趣的朋友跟隨小編一起看看吧
    2024-09-09
  • 在vue中使用回調(diào)函數(shù),this調(diào)用無(wú)效的解決

    在vue中使用回調(diào)函數(shù),this調(diào)用無(wú)效的解決

    這篇文章主要介紹了在vue中使用回調(diào)函數(shù),this調(diào)用無(wú)效的解決,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過(guò)來(lái)看看吧
    2020-08-08
  • @vue/cli4.x版本的vue.config.js常用配置方式

    @vue/cli4.x版本的vue.config.js常用配置方式

    這篇文章主要介紹了@vue/cli4.x版本的vue.config.js常用配置方式,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2022-05-05
  • 詳解Vue源碼之?dāng)?shù)據(jù)的代理訪問(wèn)

    詳解Vue源碼之?dāng)?shù)據(jù)的代理訪問(wèn)

    這篇文章主要介紹了詳解Vue源碼之?dāng)?shù)據(jù)的代理訪問(wèn),小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧
    2018-12-12

最新評(píng)論