VUE面试题

VUE面试题

v-show和v-if指令的共同点和不同(★★★★★)

相同点:都可以控制dom元素的显示和隐藏
不同点:v-show只是改变display属性,dom元素并未消失,切换时不需要重新渲染页面,适合用于频繁切换的场景;
v-if是直接将dom元素从页面删除,再次切换需要重新渲染页面

vuex是什么, 五个核心属性用法(★★★★★)

  • vuex是一个专门为Vue.js开发的状态管理模式,采用集中式存储所有组件的状态,可以解决组件之间数据共享的问题,方便后期管理与维护。
  • vuex核心:
    state:用来存放数据,相当于vue中的data。
    getters:相当于vue里的计算属性。
    mutations:是唯一可以修改state中的数据的方法,且必须是同步函数。
    actions:用于提交 mutation,而不是直接变更状态,可以包含任意异步操作。
    modules:模块化管理store,可以让每一个模块拥有自己的state、mutation、action、getters。

什么是 vue 生命周期?有什么作用(★★★★★)

Vue 实例从创建到销毁的一系列过程,总共分为8个阶段创建前/后,载入前/后,更新前/后,销毁前/后。

  • beforeCreate:创建之前,此时还没有data和methods。
  • created:创建完成,此时可以使用data和methods。
  • beforeMount:渲染之前。
  • mounted:渲染完成。
  • beforeUpdate:页面中显示的数据还是旧的,此时data数据是最新的,页面尚未和最新的数据保持同步。
  • Updated:页面和data数据已经保持同步了 ,都是最新的。
  • beforeDestroy:实例身上所有的data和所有的methods , 以及过滤器、指令等都处于可用状态,此时,还没有真正执行销毁的过程。
  • destroyed:对data的改变不会再触发周期函数,说明此时vue实例已经解除了事件监听以及和dom的绑定,但是dom结构依然存在。

组件传值方式有哪些?(★★★★★)

  • props和 $emit(父子之间 最常用):父传子是利用子组件通过props来接受数据,子传父是的方式是子组件通过$emit发送参数,父组件通过绑定自定义事件进行接收数据。
  • $parent 和 $children(父子之间 非常简洁)
  • 绑定ref: 父组件通过this.$refs可以获取子组件所有事件属性。
  • provide和inject:成对出现,用于父向下跨级传递数据。
  • bus中央事件总线(兄弟组件通信):把bus定义在vue的prototype上进行全局使用。利用this.$ bus.$emit触发事件,this.$ bus.$on监听事件。
  • vuex:vuex 是 vue 的状态管理器,存储的数据是响应式的。只需要把共享的值放到vuex中,其他需要的组件直接获取使用即可。

vue-router有几种钩子函数?(★★★★★)

1.有三个类型,分别是全局导航钩子 、路由独享钩子和组件内的钩子。

  • 全局的
    全局导航钩子主要有两种钩子:前置守卫(beforeEach)、后置钩子(afterEach)。
    前置守卫三个参数 to 、from 、next 分别的作用:
    to: Route,代表要进入的目标,它是一个路由对象。
    from: Route,代表当前正要离开的路由,同样也是一个路由对象。
    next: Function,这是一个必须需要调用的方法,而具体的执行效果则依赖 next 方法调用的参数。
    不同于前置守卫,后置钩子并没有 next 函数,也不会改变导航本身。

  • 路由独享的钩子beforeEnter 、beforeLeave
    单个路由独享的导航钩子,它是在路由配置上直接进行定义的。

  • 组件内的导航钩子
    主要有这三种:beforeRouteEnter、beforeRouteUpdate、beforeRouteLeave。他们是直接在路由组件内部直接进行定义的。

2.应用场景

  • 清除当前组件中的定时器,使用 beforeRouteLeave 将定时器进行清除
  • 关闭页面时, 将信息保存到session或Vuex中
  • 如果页面内有重要的信息需要用户保存后才能进行跳转, 或者有弹出框的情况. 应该阻止用户跳转

vue3与 vue2的区别(★★★★★)

  • 双向数据绑定原理发生了改变,vue2用的是Object.defineProperty(),vue3用的是Proxy。
  • Vue3支持碎片,就是说在组件可以拥有多个根节点。
  • Vue2使用选项式API(Options API)相比之下,Vue3使用组合式API(Composition API)。
  • 用setup()代替data;
  • vue3支持TypeScript;
  • v-if和v-for优先级,在vue2中v-for的优先级是高于 v-if 的,vue3中v-if 始终高于 v-for,但还是不建议一起使用
  • 定义全局变量的方法不一样
Vue.prototype.$http = axios //vue2
app.config.globalProperties.$http = axios //vue3
  • 生命周期不同
Vue2--------------vue3
beforeCreate  -> setup()
created       -> setup()
beforeMount   -> onBeforeMount
mounted       -> onMounted
beforeUpdate  -> onBeforeUpdate
updated       -> onUpdated
beforeDestroy -> onBeforeUnmount
destroyed     -> onUnmounted
activated     -> onActivated
deactivated   -> onDeactivated

Vue-router共有几种模式?默认是那种?(★★)

有两种模式 hash和history模式,默认是hash

  • hash ——即 URL 中的#符号以及后面的字符,hash 虽然出现 URL 中,但不会被包含在 HTTP请求中,对后端完全没有影响,因此改变 hash 不会重新加载页面。
  • history ——利用了 HTML5 的History api 中新增的pushState() 和replaceState() 方法,在这种模式下,前端的URL 必须和实际向后端发起请求的 URL 保持一致,否则返回404 错误。

Vue2和Vue3双向绑定的原理(★)

Vue2 采用数据劫持结合发布-订阅者模式的方式,通过 Object.defineProperty()来劫持各个属性的getter和setter,在数据发生改变时通知订阅者,并触发对应的监听回调,重新渲染数据。
Vue3改用Proxy 代替Object.defineProperty,因为Proxy可以直接监听对象和数组的变化,并且有多达13种拦截方法。

为什么用key,为什么不建议用index作为key(★★)

给dom元素加上key作为唯一标识 ,diff算法可以正确的识别这个节点,从而快速渲染页面。
用index作为key,不管你数组的元素顺序怎么颠倒,index都是从0开始排列的,这样会导致diff算法复用错误的旧子节点,从而降低效率。

keep-alive 的作用是什么(★)

主要是用于对需要频繁切换的组件时进行缓存,防止重新渲染dom。
1.主要有3个参数,分别是include,exclude 和 max:

  • include:只有名称匹配的组件会被缓存。
  • exclude:任何名称匹配的组件都不会被缓存。
  • max - 数字。最多可以缓存多少组件实例

2.染后 keep-alive 有两个生命周期: activated 与 deactivated,当引入keep-alive 的时候,页面第一次进入,钩子的触发顺序 created -> mounted -> activated,退出时触发 deactivated,当再次进入(前进或者后退)时,只触发 activated。

3.应用场景:

	// 将缓存 name 为 text 的组件
  	<keep-alive include='text'>
      <router-view/>
    </keep-alive>

	//在 router 目录下的 index.js 文件里
	children: [
		{
	        path: 'user',
	        component: () => import('@/views/admin/user'),
	        name: 'User',
	        meta: {
	          title: '用户管理',
	          keepAlive: false // 不需要缓存
	        }
	    }
	]
	
	//app.vue
	<template>
	  <div id="app">
	  	<keep-alive>
	      <router-view v-if="$route.meta.keepAlive"></router-view>
	    </keep-alive>
	    <router-view v-if="!$route.meta.keepAlive"></router-view>
	  </div>
	</template>

Computed和Watch的区别(★)

  • computed:是计算属性,具有缓存性,依赖其它属性值,只有依赖的属性值发生改变,才会重新计算当前computed 的值。
  • watch:没有缓存性,更多的是观察的作用,类似于某些数据的监听回调,每当监听的数据变化时都会执行回调。watch有两个参数:immediate 和 deep,immediate是组件加载立即触发,deep是深度监听。

运用场景:

  • 当我们需要进行数值计算,并且依赖于其它数据时,应该使用 computed,因为可以利用computed的缓存特性,避免每次获取值时,都要重新计算。例如购物车商品结算。
  • 当我们在数据变化时需要执行异步或开销较大的操作时,应该使用 watch。例如搜索数据。
  • 一个数据受多个数据影响,用Computed;一个数据影响多个数据,用Watch;

单页面应用优缺点?(★)

1、优点

  • 局部刷新页面,用户体验好,快,对于服务器的压力较小。
  • 前后端分离。
  • 组件化开发,维护成本低。

2、缺点

  • 首屏加载慢
  • 不利于seo
  • 页面导航不可用,如果一定要导航需要自行实现前进、后退。

$route$router的区别(★)

  • $route是“路由信息对象”,包括path,name,params,query等路由信息参数。
  • $router是“路由实例”对象,包括了路由的跳转方法,钩子函数等

封装一个组件需要注意哪些?(★)

  • 要预留插槽,因为视图结构可能不一样,由父组件决定它是怎样的结构
  • 要考虑数据的传递,定义props来接收父组件传过来的数据,同时不能直接修改props,使用$emit自定义事件,由父组件来修改
  • 业务逻辑不要在子组件中处理,因为子组件在不同的父组件中调用,业务处理代码不用,应使用 $emit 自定义事件,由父组件来处理业务

怎样理解 Vue 的单项数据流(★)

数据总是从父组件传到子组件,子组件没有权利修改父组件传过来的数据,只能请求父组件对原始数据进行修改。这样会防止从子组件意外改变父组件的状态,从而导致你的应用的数据流向难以理解。

子组件为何不可以修改父组件传递的 Prop?(★)

因为vue提倡单项数据流,即父级prop 的更新会流向子组件,反过来则不行。这是为了防止子组件意外改变父组件的状态,从而导致应用的数据流变得难以理解。

Vuex 页面刷新数据丢失怎么解决?(★)

  • 需要做 vuex 数据持久化,一般使用本地储存的方案来保存数据,可以自己设计存储方案,也可以使用第三方插件。
  • 推荐使用 vuex-persist (脯肉赛斯特)插件,它是为 Vuex 持久化储存而生的一个插件。不需要你手动存取storage,而是直接将状态保存至 cookie 或者 localStorage中。

vue组件中data为什么必须是一个函数,而不是对象?(★★)

因为组件如果被复用多次,也就会创建多个实例,如果data写成对象形式,那么组件实例共用的就是同一个data,这样会造成数据混乱。而data写成函数形式,数据以函数返回值的形式定义,这样每次复用组件的时候,都会返回一份新的data,相当于每个组件实例都有自己私有的数据空间。

v-model 的原理?(★)

v-model是v-bind和v-on的语法糖,负责监听用户的输入事件来更新数据,即是v-bind绑定表单value属性的值,v-on绑定input事件。

v-for 与 v-if 为什么不能同时使用?(★)

因为v-for 比 v-if 优先级更高,这就说明在v-for 每次的循环赋值中都会调用 一次v-if 的判断,造成性能浪费。

什么是MVVM?MVC呢?两者有什么区别?(★)

  • model-view-viewModel(MVVM)是一个软件架构设计模式,能够实现前端开发和后端业务逻辑的分离,其中model指数据模型,负责后端业务逻辑处理,view指视图层,负责前端整个用户界面的实现,viewModel则负责view层和model层的交互。
  • Controller控制视图层和数据层的关联。
  • MVVM与MVC最大的区别MVVM实现了View和Model的自动同步,不用再自己手动操作Dom元素了,即Model变化时View可以实时更新,View变化也能让Model改变。

数据更新后但是视图没有更新是怎么原因,怎么解决?(★)

使用某些方法操作数组,当数据变动时无法被vue监测,同时Vue不能检测到对象属性的添加或删除。可以使用this.$forceUpdate()或者this.$set()进行更新。

什么阶段(生命周期)才能访问操作dom?为什么?(★)

在钩子函数mounted()中才能开始访问操作dom,因为在mounted()生命周期前,dom刚好渲染好,但还未挂载到页面,如果在这之前进行dom操作,将找不到dom节点。

路由query和params传参的区别?(★)

1、query用 path匹配路由,params只能用 name匹配路由。
2、query类似 get,跳转之后页面 url后面会拼接参数。非重要性的可以这样传。params类似 post,跳转之后页面 url后面不会拼接参数。

vue自定义指令(★)

  • 私有自定义指令
//跟 data() 同级
directives:{
    color(el,binding){
        console.log('color简写')
        el.style.color = binding.value
    }
}
  • 全局自定义指令
// 全局自定义指令
Vue.directive('color' , {
  bind(el,binding){
    console.log('color简写')
    el.style.color = binding.value
  },
  update(el,binding){
    console.log('color简写')
    el.style.color = binding.value
  }
})
//简写形式:
Vue.directive('color' ,function(el,binding){
  console.log('color简写')
  el.style.color = binding.value
})

vue过滤器(★)

  • 局部过滤器
//跟 data() 同级
filters:{
    addPriceIcon(value){
        return '¥' + value
    }
}
  • 全局过滤器
Vue.filter("roundUp", (num) => {
	if (num) {
		return Math.round(num * 100) / 100
	} else {
		return num
	}
})

vue混入(★)

  • 1、定义混入
export const aaa = {
    methods: {
        showName() {
            alert(this.name)
        }
    }
}
  • 2、全局使用混入
//在 main.js 中使用
import { aaa } from './mixin'
Vue.mixin(aaa)
  • 3、局部使用混入
//在某个页面中
import { aaa } from "../mixin.js";
mixins: [aaa]

reactive 和 ref 的区别?(★)

  • ref用来定义:基本类型数据。
    reactive用来定义:对象(或数组)类型数据。
    ref也可以用来定义对象(或数组)类型数据,它内部会自动通过reactive转为代理对象。
  • ref通过Object.defineProperty()的get与set来实现响应式(数据劫持)。
    reactive通过使用Proxy来实现响应式(数据劫持),并通过Reflect操作源对象内部的数据。
  • ref定义的数据:操作数据需要.value,读取数据时模版中直接读取不需要.value
    reactive定义的数据:操作数据与读取数据:均不需要.value

vue优点

  • 轻量级框架(大小只有几十kb)
  • 简单易学(中文文档,易于理解和学习)
  • 双向数据绑定(最大的优点)
  • 组件化开发(实现了html的封装与重用)
  • 视图、数据、结构分离(数据修改更简单)
  • 虚拟dom
  • 运行速度快

vue常用指令

  • v-model 多用于表单元素实现双向数据绑定
  • v-bind 给元素绑定属性
  • v-on:给元素绑定事件
  • v-for 遍历数组
  • v-show 显示内容
  • v-hide 隐藏内容
  • v-if 显示与隐藏 (dom元素的删除添加)
  • v-else-if 必须和v-if连用
  • v-else 必须和v-if连用 不能单独使用 否则报错 模板编译错误
  • v-text 解析文本
  • v-html 解析html标签
  • v-once 只渲染元素或组件一次
  • v-cloak 解决插值闪烁问题,需要在style中设置样式[v-clock]{display:none}
  • v-pre 把标签内部的元素原位输出

vue 常用的修饰符?

事件修饰符

  • .stop 阻止事件继续传播
  • .prevent 阻止标签默认行为
  • .capture 使用事件捕获模式,即元素自身触发的事件先在此处处理,然后才交由内部元素进行处理
  • .self 只当在 event.target 是当前元素自身时触发处理函数
  • .once 事件只会触发一次
  • .passive 告诉浏览器你不想阻止事件的默认行为

v-model 的修饰符

  • .lazy 通过这个修饰符,转变为在 change 事件再同步
  • .number 自动将用户输入值转化为数值类型
  • .trim 自动过滤用户输入的收尾空格

你都做过哪些 Vue 的性能优化?PS:这里只列举针对 Vue 的性能优化,整个项目的性能优化是一个大工程。

  • 对象层级不要过深,否则性能就会差。
  • 不需要响应式的数据不要放在 data 中(可以使用 Object.freeze() 冻结数据)
  • v-if 和 v-show 区分使用场景
  • computed 和 watch 区分场景使用
  • v-for 遍历必须加 key,key最好是id值,且避免同时使用 v-if
  • 大数据列表和表格性能优化 - 虚拟列表 / 虚拟表格
  • 防止内存泄露,组件销毁后把全局变量和时间销毁
  • 图片懒加载
  • 路由懒加载
  • 异步路由
  • 第三方插件的按需加载
  • 适当采用 keep-alive 缓存组件
  • 防抖、节流的运用
  • 服务端渲染 SSR or 预渲染

$nextTick的使用

当你修改了data的值然后马上获取这个dom元素的值,是不能获取到更新后的值,你需要使用$nextTick这个回调,让修改后的data值渲染更新到dom元素之后在获取,才能成功。
在下次dom更新循坏之后执行延迟回调,在修改数据之后立即使用nextTick来获取更新后的dom

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值