vue基础(四)

devtools/2025/2/12 0:40:09/

一、计算属性 - computed

computed(计算属性)在 Vue 2 和 Vue 3 中都能使用,主要用于处理依赖响应式数据的计算逻辑,它的值会根据依赖的变化自动更新,同时有缓存,比 methods 更高效。

1. 基本使用

示例:把 message 转换为大写

<div id="app"><p>原始文本: {{ message }}</p><p>大写文本: {{ upperMessage }}</p>
</div><script>
new Vue({el: '#app',data: {message: 'hello vue'},computed: {upperMessage() {return this.message.toUpperCase()}}
})
</script>

upperMessage 依赖 message,当 message 变化时,它会自动更新

computed 有缓存只有依赖的数据变化时才会重新计算,比 methods 更高效。

2. 计算属性 vs 方法 (methods)

<div id="app"><p>{{ upperMessage() }}</p> 
</div><script>
new Vue({el: '#app',data: {message: 'hello vue'},methods: {upperMessage() {return this.message.toUpperCase()}}
})
</script>

区别

  • computed 有缓存,只在 message 变化时重新计算。
  • methods 每次调用都会重新执行,即使 message 没变,仍然会运行函数。

✅ 结论:

  • computed 处理依赖数据的计算,它只会在需要时计算,性能更好。
  • methods 处理事件或不需要缓存的逻辑

3. 计算属性的 getter 和 setter

computed 默认只有 getter(读取),但也可以加 setter(写入):

<div id="app"><input v-model="fullName"> 
</div><script>
new Vue({el: '#app',data: {fullName: '张 三'},computed: {fullName: {get() {return this.firstName + ' ' + this.lastName},set(newValue) {const names = newValue.split(' ')this.lastName = names[0]this.firstName = names[1] || ''}}}
})
</script>

4. 依赖多个属性

computed 可以依赖多个 data 变量

<div id="app"><p>{{ userInfo }}</p>
</div><script>
new Vue({el: '#app',data: {firstName: '三',lastName: '张',age: '18'},computed: {userInfo() {return `${this.lastName} ${this.firstName} - ${this.age}岁`}}
})
</script>

任何 firstNamelastNameage 变化,userInfo 都会自动更新

5. 计算属性在 Vue 3 中的写法

Vue 3 组合式 API 中,computed 需要 import: 

import { ref, computed } from 'vue'export default {setup() {const message = ref('hello vue3')const upperMessage = computed(() => message.value.toUpperCase())return { message, upperMessage }}
}

Vue 3 computed 需要 .value 访问 ref 的数据

总结

computed 计算属性的特点

  • 有缓存只有依赖数据变化时才会重新计算,比 methods 更高效。
  • 适用于依赖多个 data 属性的计算逻辑
  • 可以有 gettersetter,适用于双向绑定
  • 在 Vue 3 组合式 API 里,需要 computed(() => {}) 使用

🔹 适用场景

  • 格式化数据(大写、日期、货币格式化等)
  • 合并多个 data 变量
  • 计算总价、折扣、平均值等

🚀 如果数据要频繁计算,优先用 computed,避免 methods 造成不必要的计算!

二、监听器 - watch

watch 主要用于监听数据的变化并执行特定逻辑,适用于数据变化后需要进行异步操作、复杂逻辑或性能优化的场景。

1. 基本用法

watch 用于监听 datacomputed 里的数据变化,并在变化时执行函数。

<div id="app"><p>姓名: {{ name }}</p><input v-model="name">
</div><script>
new Vue({el: '#app',data: {name: '张三'},watch: {name(newVal, oldVal) {console.log(`姓名从 ${oldVal} 变成了 ${newVal}`)}}
})
</script>
  • name 发生变化时,watch 里的函数会被调用。
  • newVal 是新值,oldVal 是旧值。
  • 每次 input 修改 name,都会触发 watch

2. 监听多个数据

可以监听多个数据

watch: {firstName(newVal) {console.log(`firstName 变了: ${newVal}`)},lastName(newVal) {console.log(`lastName 变了: ${newVal}`)}
}

3. 监听对象或数组

(1)监听对象的某个属性

data() {return {user: { name: '张三', age: 25 }}
},
watch: {'user.age'(newVal, oldVal) {console.log(`年龄从 ${oldVal} 变成了 ${newVal}`)}
}

(2)深度监听 (deep: true)

如果监听整个对象,需要deep: true

 

data() {return {user: { name: '张三', age: 25 }}
},
watch: {user: {handler(newVal) {console.log('user 变了:', newVal)},deep: true}
}

任何 user 内部属性变化,watch 都会触发

(3)监听数组 

data() {return {items: [1, 2, 3]}
},
watch: {items: {handler(newVal) {console.log('数组变了:', newVal)},deep: true}
}

修改 items 数组(如 push/pop/splice),都会触发 watch

4. 监听 computed 计算属性

computed: {fullName() {return this.firstName + ' ' + this.lastName}
},
watch: {fullName(newVal) {console.log(`fullName 变了: ${newVal}`)}
}

 监听 computed 的值变化,适用于计算后的数据需要额外处理的情况

5. immediate 立即执行

默认情况下,watch 不会在组件创建时立即执行,但可以加 immediate: true 让它立即执行一次

watch: {name: {handler(newVal) {console.log(`初始化时就执行: ${newVal}`)},immediate: true}
}

 适用于组件初始化时就要执行的逻辑(如请求接口)。

6. 监听数据变化后执行异步操作

可以在 watch 里调用 API:

watch: {searchQuery(newVal) {clearTimeout(this.timer)this.timer = setTimeout(() => {this.fetchResults(newVal)}, 500)  // 防抖,500ms 后执行}
}

适用于搜索输入时防止频繁请求 API

7. Vue 3 watch 用法

在 Vue 3 组合式 API 中,使用 watch 需要 import

import { ref, watch } from 'vue'export default {setup() {const name = ref('张三')watch(name, (newVal, oldVal) => {console.log(`姓名从 ${oldVal} 变成了 ${newVal}`)})return { name }}
}

 Vue 3 的 watch 监听 ref 数据时,需要 .value 访问数据

总结

watch 监听数据变化,并执行指定逻辑

  • 适用于异步操作、API 请求、防抖、复杂计算
  • 监听对象/数组时,需加 deep: true
  • 监听 computed 计算属性,可处理衍生数据
  • immediate: truewatch 立即执行一次
  • Vue 3 需要 import { watch },且监听 ref 需要 .value

🚀 如果数据需要动态监听并执行操作,watch 是最佳选择!

三、过滤器 - filters

在数据被渲染之前,可以对其进行进一步处理,比如将字符截取或者将小写统一转换为大写等等,过滤器本身就是一个方法。过滤器可以定义全局或局部。

在 Vue 2 中,过滤器(filters 主要用于格式化文本,可以在 { { 插值表达式 }}v-bind 绑定中使用。它本质上是一个函数,接收输入值,返回格式化后的值

1. 全局 & 局部过滤器

Vue 2 提供全局过滤器局部过滤器两种方式。

(1)全局过滤器

Vue.filter() 中定义,全局可用。

Vue.filter('uppercase', function(value) {if (!value) return ''return value.toString().toUpperCase()
})

然后在模板中使用:

<p>{{ 'hello' | uppercase }}</p>  
<!-- 输出: HELLO -->

(2)局部过滤器

在组件的 filters 选项里定义,只在当前组件可用:

<div id="app"><!-- 输出: Hello world --><p>{{ message | capitalize }}</p>
<script>const vm = new Vue({el: '#app',data: {message: 'hello world'},filters: {capitalize(value) {if (!value) return ''return value.charAt(0).toUpperCase() + value.slice(1)}}})

2. 过滤器的多重使用

可以多个过滤器链式调用

<p>{{ message | capitalize | uppercase }}</p>

3. 过滤器用于 v-bind

v-bind 中使用时,需要用方法调用的形式:

<input :value="message | capitalize">

Vue 3 认为 filters 在模板中容易混乱,移除了 filters,建议改用计算属性(computed)或方法

<div id="app"><input :value="formattedMessage">
<script>const vm = new Vue({el: '#app',data: {message: 'hello'},computed: {formattedMessage() {return this.message.charAt(0).toUpperCase() + this.message.slice(1)}
}    })

4. 过滤器的应用场景

  • 格式化文本(如大小写转换)
  • 货币格式化
  • 时间格式化
  • 数字千分位分隔

四、混入 - Mixins

mixins(混入)是 Vue 里的一种代码复用机制,可以在多个组件之间共享逻辑,避免代码重复,提高可维护性。

1. 基本使用

创建一个 mixins,然后在组件中使用它。

// 定义一个 mixin
const myMixin = {data() {return {message: 'Hello from mixin'}},created() {console.log('Mixin 的 created 钩子被调用')},methods: {greet() {console.log(this.message)}}
}

在组件中使用 mixins

new Vue({el: '#app',mixins: [myMixin], // 这里使用 mixincreated() {console.log('组件的 created 钩子被调用')}
})

组件会继承 mixins 里的 datamethods、生命周期钩子

2. mixins 逻辑合并规则

Vue 组件和 mixins 可能有相同的 datamethods、生命周期钩子,Vue 按以下规则合并:

合并规则
data合并,但组件数据优先(mixin 里的数据不会覆盖组件)
methods合并,但组件方法优先(mixin 方法被组件覆盖)
生命周期钩子都会执行,先 mixin,后组件

3. data 合并

const myMixin = {data() {return {message: 'Hello from mixin'}}
}new Vue({mixins: [myMixin],data() {return {message: 'Hello from component'}},created() {console.log(this.message) // 输出:Hello from component}
})

data 以组件的为准,不会被 mixins 覆盖

4. methods 合并

const myMixin = {methods: {sayHello() {console.log('Hello from mixin')}}
}new Vue({mixins: [myMixin],methods: {sayHello() {console.log('Hello from component')}},created() {this.sayHello() // 输出:Hello from component}
})

如果 methods 重名,组件的 methods 会覆盖 mixins 的方法

5. 生命周期钩子合并

如果 mixins 和组件都有相同的生命周期钩子,它们都会执行,但 mixins 里的先执行

const myMixin = {created() {console.log('Mixin created')}
}new Vue({mixins: [myMixin],created() {console.log('Component created')}
})

输出顺序:

Mixin created

Component created

6. 监听器 (watch) 合并

mixins 和组件里的 watch合并执行

const myMixin = {watch: {message(newVal) {console.log('Mixin watch:', newVal)}}
}new Vue({mixins: [myMixin],data() {return { message: 'Hello' }},watch: {message(newVal) {console.log('Component watch:', newVal)}}
})

message 变化时,两个 watch 都会执行

7. 作用场景

  • 封装 API 请求(如 axios 请求)
  • 封装全局 methods(如格式化时间、数据处理等)
  • 监听路由变化
  • 公共的 watch 监听逻辑
  • 封装生命周期钩子逻辑
封装 API 请求
const fetchDataMixin = {data() {return { dataList: [] }},methods: {async fetchData(url) {const res = await fetch(url)this.dataList = await res.json()}}
}

在多个组件中复用

new Vue({mixins: [fetchDataMixin],created() {this.fetchData('https://api.example.com/data')}
})

8. Vue 3 替代方案

Vue 3 使用 Composition APIsetup() + composables)来取代 mixins

import { ref, onMounted } from 'vue'export function useFetchData(url) {const dataList = ref([])const fetchData = async () => {const res = await fetch(url)dataList.value = await res.json()}onMounted(fetchData)return { dataList }
}

在组件中使用

import { useFetchData } from './useFetchData'export default {setup() {const { dataList } = useFetchData('https://api.example.com/data')return { dataList }}
}

总结

mixins 主要用于代码复用,避免多个组件重复写相同逻辑

  • datamethodswatch、生命周期钩子都可以混入
  • methodsdata 遇到重名,组件优先
  • 生命周期钩子 遇到重名,mixins 先执行
  • 适用于封装 API 请求、监听逻辑、全局方法等

🚀 Vue 3 推荐使用 Composition API 代替 mixins,提高可读性和灵活性!

五、插件 - Plugin

Vue 的插件 (Plugins) 是一种全局增强 Vue 功能的方式,适用于全局方法、指令、组件、混入、状态管理等,例如 Vue RouterVuexElement UI 等都是 Vue 插件。

1. Vue 插件的基本结构

Vue 插件本质上是一个包含 install 方法的对象或函数

const MyPlugin = {install(Vue, options) {// 1. 添加全局方法Vue.prototype.$myMethod = function () {console.log('Hello from MyPlugin')}// 2. 添加全局指令Vue.directive('focus', {inserted(el) {el.focus()}})// 3. 添加全局混入Vue.mixin({created() {console.log('Mixin from MyPlugin')}})// 4. 注册全局组件Vue.component('MyComponent', {template: '<div>我是插件注册的全局组件</div>'})}
}export default MyPlugin

📌 插件可以:

  • 扩展 Vue 实例(如 Vue.prototype.$xxx
  • 添加全局指令
  • 注册全局组件
  • 混入全局 mixin
  • 提供全局配置

2. 在 Vue 2 中使用插件

在 Vue 组件或 main.js引入并安装插件

import Vue from 'vue'
import MyPlugin from './MyPlugin.js'Vue.use(MyPlugin) // 安装插件new Vue({el: '#app'
})

Vue.use(MyPlugin) 让所有 Vue 组件都能使用插件提供的功能。

3. Vue 2 插件的使用示例

(1)全局方法


Vue.prototype.$alertMessage = function (msg) {alert(msg)
}

组件中使用

<template><button @click="$alertMessage('Hello from Plugin!')">点击我</button>
</template>

(2)全局指令

Vue.directive('focus', {inserted(el) {el.focus()}
})

组件中使用

<template><input v-focus />
</template>

输入框会在页面加载时自动获得焦点

(3)注册全局组件

Vue.component('MyButton', {template: '<button>我是插件的按钮</button>'
})

组件中使用

<template><MyButton />
</template>

(4)全局混入 (mixin)

Vue.mixin({created() {console.log('每个组件都会执行这个 mixin')}
})

所有组件 created 时都会执行这个逻辑

4. Vue 3 中的插件

Vue 3 的插件仍然需要 install 方法,但 Vue.prototype 替换为 app.config.globalProperties

(1)创建 Vue 3 插件

const MyPlugin = {install(app, options) {// 1. 添加全局方法app.config.globalProperties.$sayHello = function () {console.log('Hello from MyPlugin')}// 2. 添加全局指令app.directive('focus', {mounted(el) {el.focus()}})// 3. 注册全局组件app.component('MyComponent', {template: '<div>我是 Vue 3 插件的组件</div>'})}
}export default MyPlugin

(2)在 Vue 3 中使用插件

import { createApp } from 'vue'
import App from './App.vue'
import MyPlugin from './MyPlugin.js'const app = createApp(App)
app.use(MyPlugin) // 安装插件
app.mount('#app')

5. 插件的应用场景

适用于全局功能扩展,如:

  1. 封装全局方法(如 axios 请求)
  2. 封装全局指令(如 v-focus 自动聚焦)
  3. 注册全局组件(如 MessageBox 组件)
  4. 提供全局 mixin(如 beforeRouteEnter 逻辑)
  5. 集成第三方库(如 Vue RouterVuexElement UI

6. 插件 vs 组件 vs mixins

对比项插件 (Plugins)组件 (Components)混入 (Mixins)
用途扩展 Vue 全局功能复用 UI 结构和逻辑复用数据逻辑
注册方式Vue.use(MyPlugin)Vue.component('MyComp', Comp)mixins: [MyMixin]
作用范围影响所有组件只在使用组件的地方生效影响 mixins 使用的组件
适用场景全局工具、API、指令复用 UI 结构复用方法、数据

http://www.ppmy.cn/devtools/158066.html

相关文章

iOS pod install一直失败,访问github超时记录

** iOS pod install一直失败&#xff0c;访问github超时记录 ** 使用nslookup github.com 查看网页所对应的IP地址 nslookup github.com 然后在进行系统配置处理&#xff0c;使用sudo进行打开 sudo nano /etc/hosts添加查询到的IP地址和对应的域名信息 20.207.73.82 githu…

ffmpeg -devices

1. ffmpeg -devices -loglevel quiet 显示ffmpeg支持的设备&#xff0c;通常用于查看ffmpeg支持的硬件设备&#xff0c;比如Cuda、Atalas 2. 输出 Devices: D. Demuxing supported .E Muxing supported DE alsa ALSA audio output E caca caca (color ASCII art) output…

C++设计模式 —— 建造者模式

C设计模式 —— 建造者模式 一个例子什么是建造者模式核心思想主要角色优点缺点适用场景 对于汉堡实现建造者模式 我们之前已经了解了单例模式&#xff0c;工厂模式&#xff0c;今天我们来学习建造者模式 一个例子 假设你是老爹汉堡店的员工&#xff0c;你知道这个店的顾客非…

Godot开发框架探索#2

前言 距离上次发文又又又隔了很长一段时间。主要原因还是因为思绪在徘徊&#xff0c;最近纠结的点有以下几个&#xff1a;1.渴求一个稳定的Godot开发框架&#xff1b;2.要不要使用更轻量的开发框架&#xff0c;或者直接写引擎&#xff1b; 3.对自己想做的游戏品类拿不定主意。…

基于Spring Boot的历史馆藏系统设计与实现(LW+源码+讲解)

专注于大学生项目实战开发,讲解,毕业答疑辅导&#xff0c;欢迎高校老师/同行前辈交流合作✌。 技术范围&#xff1a;SpringBoot、Vue、SSM、HLMT、小程序、Jsp、PHP、Nodejs、Python、爬虫、数据可视化、安卓app、大数据、物联网、机器学习等设计与开发。 主要内容&#xff1a;…

十四. Redis 新功能

十四. Redis 新功能 文章目录 十四. Redis 新功能1. ACL2. IO多线程3. 工具支持 Cluster4. 其它新功能-介绍5. 最后&#xff1a; 1. ACL ACL 参考官网&#xff1a;https://redis.io/docs/latest/operate/oss_and_stack/management/security/acl/ ACL 基本介绍&#xff1a; Re…

ArrayList和LinkedList有什么区别?在什么情况下使用ArrayList更高效?

ArrayList和LinkedList在Java中是两种常用的数据结构&#xff0c;分别基于数组和链表实现。它们在性能、内存使用和适用场景上各有特点。 ArrayList与LinkedList的主要区别 数据结构&#xff1a; ArrayList&#xff1a;基于动态数组实现&#xff0c;元素存储在连续的内存空间…

矩阵NFC碰一碰发视频的源码技术开发攻略,支持OEM

引言 在短视频与营销深度融合的当下&#xff0c;矩阵碰一碰发视频功能为商家的营销推广带来了新的活力。通过简单的碰一碰操作&#xff0c;就能快速发布视频到多个平台&#xff0c;极大地提高了营销效率。本文将深入剖析矩阵碰一碰发视频的源码技术开发&#xff0c;带你一步步…