v-if和v-show的区别
v-show
只是在display:none
和display:block
之间切换,只需要切换CSS,DOM一直保留着, v-show
在初始渲染时,开销更高,但是切换开销很小,比较适合频繁切换的场景
v-if
涉及到 vue 的底层编译,当属性初始为false
时,组件不会被渲染,直到条件变为true
,且切换条件时,会触发销毁/挂在组件,切换时开销更高,更适合不常切换的场景。
active-class是哪个组件的属性?
active-class
是 vue-router 模块中router-link
组件的属性
对keep-alive的理解
keep-alive
是一个内置组件,可使被包含的组件保留状态,或避免重新渲染,有include
(包含的组件被缓存)和 exclude
(排除的组件不被缓存) 两个属性。
使用方法
<keep-alive include="include_components" exclude="exclude_components">
<component>
<!-- 该组件是否缓存取决于include和exclude属性-->
</component>
</keep-alive>
参数解释
include
- 字符串或正则表达式,只有name匹配的组件会被缓存
exclude
- 字符串或正则表达式,任何名称匹配的组件都不会被缓存
include
和 exclude
的属性允许组件有条件地缓存,二者都可以用","分割字符串、正则表达式、数组。
当使用正则或者数组是,要记得使用v-bind
使用示例
<!-- 逗号分割字符串,只有组件 a 和 b 被缓存 -->
<keep-alive include="a,b">
<component></component>
</keep-alive>
<!-- 正则表达式(需要使用 v-bind,符合匹配规则的都会被缓存) -->
<keep-alive :include="/a|b/">
<component></component>
</keep-alive>
<!-- Array (需要使用 v-bind,被包含的都会被缓存) -->
<keep-alive :inclide="['a', 'b']">
<component></component>
</keep-alive>
extend 能做什么
作用是扩展组件生成一个构造器,通常与$mount
一起使用
// 创建组件构造器
let Component = Vue.extend({
templage: '<div>test</div>'
})
// 挂在到#app上
new Component().$mount('#app')
// 扩展已有组件
let SuperComponent = Vue.extend(Component)
new SuperComponent({
created(){
console.log(1)
})
})
new SuperComponent().$mount('#app')
如何使用vue.$nextTick()
nextTick
可以使我们在下次DOM 更新循环结束之后执行延迟回调,用于获得更新后的DOM
data: function() {
return {
message: '没有更新'
}
},
methods: {
updateMessage: function() {
this.message = '更新完成'
console.log(this.$el.textContent) // 没有更新
this.$nextTick(function() {
console.log(this.$el.textContent) // 更新完成
})
}
}
vue双向数据绑定原理的理解
vuejs 是采用 数据劫持, 结合发布者-订阅者模式 的方式,通过Object.defineProperty()
来劫持各个属性的setter
,getter
。在数据变动时发布消息给订阅者, 触发相应的监听回调。
MVVM作为数据绑定的入口,整合Observer
, Compile
和Watcher
三者,通过Observer
来监听自己的model
数据变化,通过Compile
来解析编译模板(解析{{}}),最终利用Watcher
搭起 Observer
和Compile
之间的通信桥梁,达到数据变化 => 视图更新; 视图交互变化 input => 数据model变更的双向绑定效果
MVVM 和 MVC的区别
MVC, backone.js就是使用的这种模式
由Model
,Controller
,View
组成,
Model
负责保存应用数据,与后端数据进行同步;
Controller
负责业务逻辑,根据用户行为对Model数据进行修改
View
负责视图展示,将model中的数据可视化
缺点: 数据流混乱,model
和view
数据交互,维护非常麻烦;view
比较庞大
MVVM
可分解成Model
,View
, ViewModel
View
和Model
之间被分离开来,互相不知道对方的存在
优点:低耦合高内聚,View
可以独立于Model
的变化和修改,可重用性,独立开发,可测试
vue为什么采用Virtual Dom
创建真实 DOM 的代价高:真实的 DOM 节点 node
实现的属性很多,而 vnode
仅仅实现一些必要的属性,相比起来,创建一个 vnode
的成本比较低
触发多册浏览器重绘及回流:使用vnode
,相当于加了一个缓冲,让一次数据变动所带来的所有 node
变化, 先在vnode
中进行修改,然后 diff
之后对所有产生差异的节点集中一次对DOM tree
进行修改,以减少浏览器的重绘及回流
虚拟dom由于本质是一个js对象,因此天生具备跨平台的能力,可以实现在不同平台的准确显示。
Vritual DOM 在性能上的收益不是最主要的,更重要的是他使得Vue具备了现代框架应有的高级特性
Vuex是什么,怎么使用?哪些场景使用它
只用来读取的状态集中放在store
中;改变状态的方式是提交mutations
,这是个同步的事物;异步逻辑应该封装在action
中。
在main.js引入store
,注入。新建一个目录store
,…export
场景有:单页面应用中,组件之间的状态,音乐播放、登录状态、加入购物车
state
Vuex 使用单一状态树,即每个应用将仅仅包含一个store
实例,但单一状态树和模块化并不冲突。存放的数据状态,不可以直接修改里面的数据。
mutations
mutations
定义的方法动态修改Vuex的store
中的状态或数据。
getter
类似 vue 的计算属性,主要用来过滤一些数据。
action
action
可以理解为通过将mutations
里面处理数据的方法变成可异步处理数据的方法,简单的说就是异步操作数据。view层通过store.dispath
来分发action
。
// store实例
const store = new Vuex.Store({
state: {
count: 0
},
mutations: {
increment(state){
state.count++;
}
},
actions: {
increment(state) {
context.commit('increment')
}
}
});
modules
项目特别复杂的时候,可以让每一个模块拥有自己是state、mutation、action、getters
,使得结构非常清晰,方便管理。
const moduleA = {
statue: {...},
mutations: {...},
actions: {...},
getters: {...}
}
const moduleB = {
statue: {...},
mutations: {...},
actions: {...}
}
const store = new Vuex.Store({
modules: {
a: moduleA,
b: moduleB
}
})
Vue路由的钩子函数
首页可以控制导航跳转,beforeEach
, afterEach
等,一般用于页面 title 的修改。一些需要登录才能调整页面的重定向功能、
beforeEach
主要有3个参数to, from, next
:
to
: route 即将进入的目标路由对象,
from
: route 当前导航正要离开的路由,
next
: function
一定要调用该方法 resolve 钩子。执行效果依赖next
方法的调用参数,可以控制网页的跳转。
Vue的路由实现:hash模式和history模式
hash
模式:在浏览器中符号 #
,#
以及#
后面的字符称之为hash
,用window.location.hash
读取;
特点:hash
虽然在URL中,但不被包括在HTTP请求中;用来指导浏览器动作,对服务器安全无用,hash
不会重加载页面。
history
模式:history
采用HTML5的新特性;且提供了两个新方法:pushState, replaceState
可以对浏览器历史记录栈进行修改,以及 popState
事件的监听到状态变更。
history
模式下,前端的URL必须和实际后端发起请求的URL一致,如
http://www.xxx.com/items/id。后端如果缺少对/items/id
的路由处理,将返回404错误。
Vue-Router官网里描述: 如果要完好这种模式,需要后台配置支持…所以呢,你要在服务端增加一个覆盖所有情况的候选资源,如果URL匹配不到任何静态资源,则应该返回同一个index.html
页面,这个页面就是你app依赖的页面。