一、Vue3架构革新
1.1 响应式系统重写
Vue3使用Proxy替代了Vue2的Object.defineProperty,带来了显著的性能提升和功能增强:
-
全范围的响应式检测:可以检测对象属性的添加/删除
-
更好的数组支持:直接监听数组变化无需hack
-
更高效的内存使用:惰性响应式处理
-
嵌套对象自动解包:无需特殊处理
1.2 虚拟DOM优化
Vue3的虚拟DOM进行了多项优化:
-
编译时静态节点标记:跳过静态子树比对
-
区块树(Block Tree):动态节点追踪更精确
-
缓存事件处理函数:避免不必要的重新渲染
-
更高效的diff算法:最长递增子序列优化
二、组合式API核心概念
2.1 setup函数
setup是组合式API的入口点,在组件创建之前执行:
setup特性:
-
在beforeCreate之前调用
-
没有this上下文
-
返回的对象会暴露给模板
-
可以返回渲染函数
2.2 响应式基础
2.2.1 ref与reactive
| 特性 | ref | reactive |
|---|---|---|
| 创建方式 | ref(value) |
reactive(object) |
| 访问值 | .value |
直接访问属性 |
| 适用场景 | 基本类型/对象引用 | 复杂对象 |
| 模板自动解包 | 需要.value但在模板中自动解包 | 直接使用 |
const counter = ref(0); // 基本类型
const user = reactive({ name: 'Bob' }); // 复杂对象
// 在JS中
counter.value++;
user.name = 'Alice';
// 在模板中
// <div>{{ counter }}</div>
// <div>{{ user.name }}</div>
2.2.2 computed与watch
计算属性:
const double = computed(() => count.value * 2);
侦听器:
// 单个源
watch(count, (newVal, oldVal) => {
console.log(`count变化: ${oldVal} -> ${newVal}`);
});
// 多个源
watch([count, user], ([newCount, newUser], [oldCount, oldUser]) => {
// 响应变化
});
2.3 生命周期钩子
组合式API的生命周期钩子:
| 选项式API | 组合式API |
|---|---|
| beforeCreate | 不需要(使用setup代替) |
| created | 不需要(使用setup代替) |
| beforeMount | onBeforeMount |
| mounted | onMounted |
| beforeUpdate | onBeforeUpdate |
| updated | onUpdated |
| beforeUnmount | onBeforeUnmount |
| unmounted | onUnmounted |
| errorCaptured | onErrorCaptured |
import { onMounted, onUnmounted } from 'vue';
setup() {
onMounted(() => {
console.log('组件挂载完成');
});
onUnmounted(() => {
console.log('组件即将卸载');
});
}
三、逻辑复用模式
3.1 自定义组合函数
将相关逻辑提取为可复用函数:
// useCounter.js
import { ref } from 'vue';
export function useCounter(initialValue = 0) {
const count = ref(initialValue);
function increment() {
count.value++;
}
function decrement() {
count.value--;
}
return {
count,
increment,
decrement
};
}
// 组件中使用
import { useCounter } from './useCounter';
export default {
setup() {
const { count, increment } = useCounter(10);
return {
count,
increment
};
}
};
3.2 与第三方库集成
将第三方库封装为组合函数:
// useMouse.js
import { ref, onMounted, onUnmounted } from 'vue';
export function useMouse() {
const x = ref(0);
const y = ref(0);
function update(event) {
x.value = event.pageX;
y.value = event.pageY;
}
onMounted(() => window.addEventListener('mousemove', update));
onUnmounted(() => window.removeEventListener('mousemove', update));
return { x, y };
}
四、与模板的交互
4.1 模板引用(ref)
访问DOM元素或组件实例:
<template>
<input ref="inputRef" />
</template>
<script>
import { ref, onMounted } from 'vue';
export default {
setup() {
const inputRef = ref(null);
onMounted(() => {
inputRef.value.focus();
});
return {
inputRef
};
}
};
</script>
4.2 依赖注入(provide/inject)
跨组件层级传递数据:
// 祖先组件
import { provide, ref } from 'vue';
setup() {
const theme = ref('dark');
provide('theme', theme);
return {
theme
};
}
// 后代组件
import { inject } from 'vue';
setup() {
const theme = inject('theme', 'light'); // 默认值'light'
return {
theme
};
}
五、TypeScript集成
5.1 组件Props类型定义
interface Props { title: string; size?: 'small' | 'medium' | 'large'; disabled?: boolean; } export default defineComponent({ props: { title: { type: String as PropType<Props['title']>, required: true }, size: { type: String as PropType<Props['size']>, default: 'medium' }, disabled: Boolean }, setup(props: Props) { // 使用props } });
5.2 组合函数类型定义
import { Ref } from 'vue';
interface CounterOptions {
min?: number;
max?: number;
}
interface CounterReturn {
count: Ref<number>;
increment: () => void;
decrement: () => void;
}
export function useCounter(
initialValue = 0,
options: CounterOptions = {}
): CounterReturn {
const count = ref(initialValue);
function increment() {
if (options.max !== undefined && count.value >= options.max) return;
count.value++;
}
function decrement() {
if (options.min !== undefined && count.value <= options.min) return;
count.value--;
}
return {
count,
increment,
decrement
};
}
六、最佳实践
6.1 代码组织原则
-
按功能而非选项类型组织代码:
-
将相关的数据、计算属性、方法放在一起
-
避免将setup函数变成"大杂烩"
-
-
合理拆分组合函数:
-
保持组合函数单一职责
-
控制组合函数复杂度
-
-
命名规范:
-
组合函数使用use前缀(如useFetch)
-
ref变量保持描述性命名
-
6.2 性能考量
-
避免不必要的响应式:
// 不需要响应式的数据 const staticData = { title: 'About' }; -
合理使用shallowRef/shallowReactive:
const largeList = shallowRef([]); // 内部不转换响应式 -
优化计算属性:
// 只有当依赖变化时才重新计算 const filteredList = computed(() => largeList.value.filter(item => item.active) );
Vue3的组合式API代表了前端组件设计的新范式,它通过更灵活的代码组织方式、更好的TypeScript集成和更高效的逻辑复用能力,显著提升了复杂组件的可维护性。掌握这些核心概念和技术要点,开发者能够构建更健壮、更易扩展的Vue应用程序