1.Vue的数据请求方式
(1)Vue-resource
(2)Axios(封装的第三方库)
(3)Fetch
(4)Ajax
2.Vuex的属性
(1)State,是vuex的基本属性,用来存储变量
(2)Getters,是state的计算属性
(3)Mutation,同步更新数据方法,用同步方法更新数据符合数据库的独立性原则
(4)Action,异步更新数据方法
(5)Modules,模块化vuex,将store分割为多个moudle
3.Vue实现双向绑定原理
Vue响应系统,其核心有三点:observe、watcher、dep:
- observe:遍历data中的属性,使用 Object.defineProperty 的get/set方法对其进行数据劫持;在3.0中使用了更优秀的proxy方法,解决了无法监听通过数组下标对数组的改动的问题。
- dep:每个属性拥有自己的消息订阅器dep,用于存放所有订阅了该属性的观察者对象
- watcher:观察者(对象),通过dep实现对响应属性的监听,监听到结果后,主动触发自己的回调进行响应
computed的实现方法:每个 computed 属性都会生成对应的观察者(Watcher 实例)来对相应数据进行监听
<!DOCTYPE html>
<html>
<head>
<meta charset="{CHARSET}">
<title></title>
</head>
<body>
<p></p>
<input type="text">
</body>
<script>
let p = document.querySelector('p');
let inp = document.querySelector('input');
let obj = {
msg: 'hello'
}
p.innerText = obj.msg
inp.value = obj.msg
//实现视图变化数据跟着变化
inp.oninput = function () {
// console.log(inp.value);
obj.msg = inp.value
// console.log(obj.msg);
}
//实现数据变化视图跟着变化
let temp = obj.msg
Object.defineProperty(obj, 'msg', {
get() {//get方法会劫持msg这个属性的获取操作
return temp
},
set(value) {//set方法会劫持msg这个属性的设置操作
temp = value
p.innerText = temp
inp.value = temp
}
})
</script>
</html>
4.vuex原理
参考文章https://blog.csdn.net/weixin_42935546/article/details/90199813
Vuex是专门为vue设计的状态管理工具(vue是构建用户界面的渐进式js框架),采用集中式存储管理应用的所有组件的状态,并以相应的规则保证状态以一种可预测的方式发生变化。
state:驱动应用的数据源
view:以声明方式将state映射到视图上
actions:响应view上的用户输入导致的状态变化
vuex最核心的是store,store包含着大部分的state。store不能被直接修改,一定要触发mutation才能对store中的内容进行修改。
vuex的原理:所有组件共享一份数据,它为什么能实现所有的组件共享同一份数据?
因为vuex生成了一个store实例,并且把这个实例挂在了所有的组件上,所有的组件引用的都是同一个store实例。
store实例上有数据,有方法,方法改变的都是store实例上的数据。由于其他组件引用的是同样的实例,所以一个组件改变了store上的数据,导致另一个组件上的数据也会改变,就像是一个对象的引用。
5.vue怎么实现页面的权限控制
利用 vue-router 的 beforeEach 事件,可以在跳转页面前判断用户的权限(利用 cookie 或 token),是否能够进入此页面,如果不能则提示错误或重定向到其他页面,在后台管理系统中这种场景经常能遇到。
6.mounted的常用方法
mounted:html加载完成后执行。执行顺序:子组件-父组件。
7.钩子函数
- created和mounted中间编译模板,生成html
beforeCreate(创建实例)、
created(创建完成)创建实例,初始化(顺序props、methods、data、computed、watch),编译生成html模板
beforeMount(开始创建模板)、
mounted(创建完成)、el 被新创建的 vm.$el 替换,并挂载到实例上去之后调用该钩子。渲染dom节点。
beforeUpdate(开始更新)、
updated(更新完成)、重新渲染dom
beforeDestroy(开始销毁)、
destroyed(销毁完成)销毁实例
8.计算属性和监听器有什么区别?computed、watch
watch是观察某一个属性的变化,重新计算属性值。computed是通过所依赖的属性的变化重新计算属性值。
大部分情况下watch和computed几乎没有差别。但如果要在数据变化的同时进行异步操作或者是比较大的开销,那么watch为最佳选择。 computed好,因为他可以缓存。
watch特点:①可接受两个参数;②监听时可触发一个回调,并做一些事情;③监听的属性必须是存在的;④允许异步
computed特点:①有缓存机制;②不能接受参数;③可以依赖其他computed,甚至是其他组件的data;④不能与data中的属性重复
watch的原理:当属性内容发生变化时将dirty变为true,然后重新渲染重新计算。
watch可以深度监听,computed可以缓存
9.v-for渲染列表是key是用来做什么的
一句话:为了高效的更新虚拟DOM
详解:
不加key,更新每一项,效率低,采用就地复用策略。加,根据唯一的key值对dom进行定位,进行dom的交换移动或者单独的dom更新,效率高。
id作key与index作key的区别:id作key更适合单个元素的重新渲染,其他作key仍会触发全部的重新渲染。
10.数据请求在生命周期哪一个阶段
看实际情况,一般在 created(或beforeRouter) 里面就可以,如果涉及到需要页面加载完成之后(需要操作dom元素)的话就用 mounted。
11.router实现方式原理[hash、history]
1、Hash模式:
hash模式背后的原理是html5的onhashchange事件,可以在window对象上监听这个事件。然后根据location.hash来进行页面跳转。
在url的"#"后改变hash值,浏览器只会滚动到相应位置,不会导致浏览器向服务器发出请求,浏览器不发出请求,也就不会刷新页面。vue-router默认用hash。
缺点:只能改hash值
2.history
能让开发人员在不刷新整个页面的情况下修改站点的URL,就是利用 HTML5的history.pushState API 来完成 URL 跳转而无须重新加载页面,将页面信息保存在state中。
缺点:后端不设置的话,如果path中的资源请求不到会404
12.keep-alive有什么作用
keep-alive 可以使被包含的组件保留状态,或避免重新渲染,特别是v-if的内容不会触发destory
13.vue的核心思想
数据驱动和组件化
数据驱动:通过给数据和视图中间创建一个watcher监听数据的变化,当视图的依赖数据发生改变时,watcher通知视图进行重新渲染。
14.重新渲染组件的方法
1.v-if
2.key
15.diff算法复用的是什么
复用那些不需要修改的dom节点
16.虚拟dom和真实dom的区别
1.what
虚拟DOM是真实DOM结构的映射,即一个数据集合,虚拟可以映射到真实dom上。
虚拟dom也叫Vnode,当需要渲染视图的时候就依据Vnode生成新dom元素或者根据Vnode缓存修改真实dom。
2.why
真实dom修改时,浏览器会重新进行布局设计,这样频繁操作会降低浏览器性能。虚拟dom修改后与真实dom进行增删改查,然后重绘较少的节点。
3.diff算法
diff算法是虚拟节点的核心。
diff算法复用相同节点,对不同节点进行更新。
具体有四种复用优化方法,不行再用循环:
新前新后,旧前旧后
1.新前 == 旧前,直接更新,不需要移动
2.新后 == 旧后,直接更新,不需要移动
3.新后 == 旧前,更新后把节点移动到末位
4.新前 == 旧后,更新完后把节点移动到前端
17.webpack原理
webpack就是一个模块打包工具。
webpack是收把项目当作一个整体,通过webpack.config.js,在module
中配置里查找,然后根据rules
中的test
选择一个loader来处理。
loader的作用:
1、实现对不同格式的文件的处理,比如说将scss转换为css,或者typescript转化为js
2、从而使其能够被添加到依赖图中
plugin的作用
使用plugins
让打包变的便捷,可以在webpack打包的某时刻帮做一些事情比如生成html文件或者清除dist文件夹或者是将loader打包的css生成独立的css而不是内嵌在js中。
1.
new HTMLWebpackPlugin()
//生成新html
new ExtractTextPlugin('main.css')
//css生成独立的css而不是内嵌在js中
参见https://segmentfault.com/a/1190000011383224
18.Vue响应式系统为什么不监听数组
vue3.0的双向数据绑定时是可以通过proxy监听数组的,2.0只能对数组的操作进行监听来达到对数组的监听,但无法监听到通过下标的改动。
对于watch是无法监听数组的,但是通过handler+deep:true还是可以监听的
19.Vue中的scoped实现原理
scoped作用是实现组件样式模块化,防止污染全局。
scoped的实现原理是PostCSS,转译后给组件添加一个独一无二的动态属性。
20.vue$相关元素解释
vm.$el
获取Vue实例关联的DOM元素;
vm.$data
获取Vue实例的data选项(对象)
vm.$options
获取Vue实例的自定义属性(如vm.$options.methods,获取Vue实例的自定义属性methods)
vm.$refs
获取页面中所有含有ref属性的DOM元素(如vm.$refs.hello,获取页面中含有属性ref = “hello”的DOM元素,如果有多个元素,那么只返回最后一个)
vm.$nextTick
由于事件轮询机制页面不会立即更新,所以等到下一次更新再执行。特别是对于mounted或created,如果需要操作渲染后的视图,也要使用 nextTick 方法。
21.多层父子组件传递消息方法,父子组件如何获取对方数据
- v-bind="$attrs"
将父组件中传下来但是当前组件没有用props接受的部分继续向下传递
v-on="$listeners"
相反,将子组件传上来的但是当前没有往上传的emit继续往上传 - provide
将provide内容全部传递给子组件,inject将provide的所有内容都拿到 - 直接通过$parent或$children对子组件或父组件内容进行修改
vm.$on(“eventName”,function(value){})
添加绑定事件
1.$children,缺点遍历的顺序不固定,也不是响应式数据;$parent,同理
2.$refs,组件注册
22.promise.all与promise.race
一个是并发,接受数组,返回数组,一个是赛跑,接受数组返回单例。
23.插槽
作用:将标签内内容插入到组件对应位置。
后背内容:slot标签中有默认内容
具名插槽:
//外层内容,用template包围,v-slot写对应名字
<template v-slot:footer>
<p>Here's some contact info</p>
</template>
//内层具名插槽
<slot name="header"></slot>
作用域插槽:外面插槽想用里面的变量
//外层内容,用template包围,v-slot写对应名字,赋值
<template v-slot:default="slotProps">
{{ slotProps.user.firstName }}
</template>
//内层插槽,数据绑定,提供给外层赋的值
<slot v-bind:user="user">
{{ user.lastName }}
</slot>
24.vue怎么实现热更新
1.服务端(node)与客户端建立EventSource通道,类似于websocket,更轻量级。
2.webpack监听到修改重新编译,完成后通知客户端发起请求获得热更新补丁。
3.客户端请求拿到补丁后插入html,触发重新渲染
25.$set
vue存在的问题:如果在实例创建之后添加新的属性到实例上,它不会触发视图更新
当一个数据为响应式时,vue会给该数据添加一个__ob__属性,因此可以通过判断target对象是否存在__ob__属性来判断target是否是响应式数据,当target是非响应式数据时,我们就按照普通对象添加属性的方式来处理;当target对象是响应式数据时,我们将target的属性key也设置为响应式并手动触发通知其属性值的更新。
具体的做法就是进行数据劫持然后初始化其消息订阅器。
26.vue的更新策略
Vue 在修改数据后,视图不会立刻更新,而是等同一事件循环中的所有数据变化完成之后,再统一进行视图更新。