Vue//总结

Vue
vue是什么?有什么功能?有什么优点?
1、vue 是一个轻量级的前端框架语言。用于创建 web 交互界面的库,是一个精简的 MVVM。通过双向数据绑定把 view 层和 model 层连接了起来。
2、功能:
① 数据渲染 / 数据同步
② 模块化 / 组件化
③ 其它:路由、ajax、数据流
3、优点:
① 体积小,压缩后只有33k;
② 运行效率高,虚拟dom,预先通过JavaScript进行各种计算,把最终的dom操作计算出来并优化;
③ 双向数据绑定,可减少dom操作,专注于业务逻辑上;
④ 学习资源多、成本低,基于vue的组件、ui框架都比较多。

MVVM
M - Model,数据模型
V - View,将数据模型转换为UI
VM - ViewModel,监听数据的改变、控制视图行为。

mvvm 和 mvc 区别?
mvc 中 Controller 演变成 mvm 中的 viewModel。
mvvm 解决了 mvc 中大量的 DOM 操作使页面性能降低、加载速度慢、影响用户体验的问题。

vue生命周期有哪些?
vue生命周期总共分为8个阶段:创建前后、载入前后、更新前后、销毁前后。(beforecCreate created beforeMount mounted beforeUpdate updated beforeDestroy destroyed)

  • 创建前后:
    beforeCreate阶段,实例初始化之后, el 和 数据对象data 都为 undefined。
    created阶段,vue实例已经创建。数据观测,property和方法的运算,watch/event事件回调。无 $el。
  • 载入前后:
    beforeMount阶段,vue实例的 e l 和 d a t a 都 初 始 化 了 , 但 挂 载 之 前 为 虚 拟 的 d o m 节 点 , d a t a . m e s s a g e 还 未 替 换 。 m o u n t e d 阶 段 , v u e 实 例 挂 载 完 成 , e l 被 新 创 建 的 v m . el 和 data 都初始化了,但挂载之前为虚拟的dom节点,data.message还未替换。 mounted阶段,vue实例挂载完成,el被新创建的vm. eldatadomdata.messagemountedvueelvm.el替换了。data.message成功渲染。
  • 更新前后:
    data变化时,会触发。
  • 销毁前后:
    vue实例销毁,解除相关事件监听和dom的绑定。

每个生命周期适合那些场景?
(beforeCreate、created、mounted、updated、beforeDestroyed、nextTick)
beforeCreate:添加loading事件,在加载实例时触发;
created:实例创建、初始化完成,渲染页面结构有关的数据请求;
mounted:挂在元素,获取dom节点;进行ajax交互。(此时页面已经渲染出来,异步请求实现页面局部更新,普通数据请求)
updated:数据变动后,可以在这些函数统一处理数据
beforeDestroyed:实例销毁前可以做一个停止销毁or确认框
nextTick:数据更新后立即操作dom

vue第一次页面加载会触发哪几个钩子函数?
beforeCreate created beforeMount mounted

DOM渲染在哪个周期已经完成?
mounted

ajax 放在哪个生命周期?
mounted
生命周期是同步执行的,ajax 是异步执行的。

created和mounted的区别。在那个阶段前发送数据请求比较好。
created:在模板渲染成html前调用,通常初始化某些属性,然后渲染成视图。
mounted:在模板渲染成html后调用,通常初始化页面后、再对html的dom节点进行一些需要的操作。
在created之前发送数据请求比较好,因为这个时候数据观测完毕。若在mouted前可能会出现闪屏的问题。

父子组件声明周期的顺序(渲染过程、更新过程、销毁过程)

  • 渲染过程顺序:
    父 beforeCreate -> 父 created -> 父 beforeMounted -> 子 beforeCreate -> 子 created -> 子 beforeMounted -> 子 mounted -> 父 mounted
  • 更新过程
    父 beforeUpdate -> 子 beforeUpdate -> 子 updated -> 父 updated
  • 销毁过程
    父 beforeDestroy -> 子 beforeDestroy -> 子destroyed -> 父 destroyed

父组件 可以监听子组件 的生命周期吗?
可以。用 @hook:
<child @hook:mounted=“getMounted”>

vue 中的事件修饰符主要有哪些?分别是什么作用?
.stop——阻止冒泡事件
.prevent——阻止默认事件
.native——绑定原生事件
.once——事件只执行一次,相当于阻止事件冒泡
.self——将事件绑定在自己身上,相当于阻止事件冒泡
.caption

v-show、v-if区别
v-show是css切换,v-if是完整销毁和重新创建
频繁切换用v-show,变动较少用v-if
v-if=“false”时不会渲染

v-for 和 v-if 为什么不能连用?
v-for 优先级高于 v-if。若连用,会把 v-if 的每个元素都添加一下,造成性能问题。

vue常用指令及用法
v-text、v-html
条件渲染——v-show。v-if. v-else-if. v-else
列表渲染——v-for
事件处理——v-on
表单输入绑定——v-bind、v-model
v-slot
v-pre
v-clock
v-once(只渲染元素和组件一次)

组件之间的传值
1、父组件向子组件传值 props
props 可以 定义接收的数据类型
用 v-model 动态传值
2、子组件向父组件传值 emit
通过 emit 触发父组件中的事件
3、不同组件间传值 eventBus(小项目用eventBus,大项目用vuex)
定义一个新的vue实例专门用于传递数据,并导出
在需要相互通信的组件之中,都引入bus
定义传递的方法名和传输内容,点击事件或钩子函数触发Bus. e m i t 事 件 。 另 一 组 件 通 过 B u s . emit事件。另 一组件通过Bus. emitBus.on监听事件
接收传递过来的数据
4、不同组件间传值 vuex
vuex是状态管理模式,可以实现父子组件、兄弟组件间的传值,尤其适用于中大型项目开发。

路由跳转方式

js用 router.push(’/…’)

computed、watch、method有什么区别?
computed:有缓存性。多用于计算值的场景,若依赖其他数据,可以把这个数据设计为computed。
watch:无缓存性,页面重新渲染但值没有变化时也需要执行。若需要在某个数据变化时做一些事情,使用watch来观察数据的变化。
method:只要把方法用到模板上了,每一次变化就会重新渲染视图,性能开销大。

key
key可以使操作更准确、更快速,避免相同类型元素被重复渲染。可以删除没有key的值保证准确性。

组件中的data为什么是函数?
因为组件是需要被复用的,js里对象是引用关系,这样作用域没有隔离。
而new Vue的实例,是不会被复用的,因此不存在引用对象问题。

class和style如何动态绑定?
都可以通过 对象语法、数组语法 来动态绑定。

vue的单向数据流
所有的prop都使得父子prop之间形成一个 单向下行 绑定:父级prop的更新会向下流动到子组件中,但是反过来不行。防止子组件以外改变父组件的状态,导致数据流难以理解。

keep-alive
keep-alive 是 vue 内置的一个组件,可以是被包含的组件保留状态,避免重新渲染;
特性:
① 一般结合路由和动态组件一起使用,用于缓存组件;
② 提供 include 和 exclude 属性,包含就缓存,不包含不缓存。
优先级:exclude > include
③ 对应两个钩子函数 activated 和 deactivated。组件激活,触发 activated;组件移除,触发 deactivated。

v-model 的原理
v-model 可以看成是 value+input 方法的语法糖(组件)。原生的 v-model ,会根据标签的不同生成不同的事件与属性。
vue中使用 v-model 指令 在表单text、textarea、checkbox、radio、select 等元素上创建数据双向绑定,v-model 实际上只是一个语法糖,它内部是 不同的输入内容 使用 不同的属性 并 抛出不同的事件:

  • text、textarea 元素使用 value 属性和 input 事件;
  • checkbox、radio 元素使用 checked 属性和 change 事件;
  • select 字段将 value 作为 prop 并将 change 作为事件。

为什么Vue采用异步渲染呢?
Vue 是组件级更新,如果不采用异步更新,那么每次更新数据都会对当前组件进行重新渲染,所以为了性能, Vue 会在本轮数据更新后,在异步更新视图。核心思想 nextTick 。

nextTick()
在数据修改后,立即使用这个回调函数,获取更新后的DOM。
异步方法,异步渲染最后一步,与JS事件循环联系紧密。主要使用了宏任务微任务(setTimeout、promise那些),定义了一个异步方法,多次调用nextTick会将方法存入队列,通过异步方法清空当前队列。

vue插槽

  • 单个插槽:
    当子组件模板只有一个没有属性的插槽时,父组件传入的整个内容片段将插入到插槽所在的dom位置,且替换掉插槽标签本身;
  • 命名插槽:
    子组件可以有有多个不同特性name的插槽,父组件中调用时使用<tempalete v-slot:"…">来根据插槽name将内容分发到对应的位置。
  • 作用域插槽
    带数据的插槽,为了能让父组件访问子组件中的数据,子组件插槽中,父组件调用组件时<template v-slot="变量“>变量会接收从子组件传过来的prop对象。

vue-router有哪几种导航钩子?导航解析全过程?
路由守卫:通过跳转or取消的方式进行导航守卫。
3种
① 全局导航钩子:router.beforeEach((to,from,next)=>{…})、router.beforeResolve、router.afterEach
② 路由独享守卫钩子:beforeEnter
③ 组件内钩子:beforeRouteEnter、beforeRouteUpdate、beforeRouteLeave
导航解析全过程:
DOM
↗ ↗ ↘ ↘
导航失活组件 →→→→←←←← 全局 →→→→←←←← 重激活组件新激活组件
↙ ↗↙ ↗
路由

谈谈你对vuex的理解
vuex是一个状态管理模式,相当于一个仓库。
1、状态字管理应用
单向数据流-容易受破坏

2、多组件共享状态
多个视图依赖于同一状态。有5中属性:state、getter、action、mutation、module。

  • state:vuex使用单一状态树,即每个应用仅仅包含一个store。用于存放数据状态,不可以直接修改里面的数据;
  • mutation:定义的方法动态修改 vuex 的 store 中的状态或数据;通过 store.commit 触发;
  • getter:相当于 vue 的计算属性,主要用来过滤一些数据;
  • action:定义的方法用于异步操作数据。view层通过 stroe.dispatch 来分发 action
    3、vuex 一般用于中大型单页面应用,对于一些组件间关系较为简单的小型应用,使用组件prop属性或事件来完成组件间传值即可。

你有对 Vue 项目进行哪些优化?
一、代码层面的优化

  • v-if 和 v-show 区分使用场景
  • computed 和 watch 区分使用场景
  • v-for 遍历必须为 item 添加 key,且避免同时使用 v-if
  • 长列表 / 无限列表 性能优化
  • 图片 / 路由 懒加载
  • 事件的销毁
  • 第三方插件按需引入
  • 服务端渲染 SSR or 预渲染
    二、Webpack 层面的优化
  • webpack 对图片进行压缩
  • 减少 ES6 转为 ES5 的冗余代码
  • 提取公共代码
  • 提取组件的 CSS
  • 模板预编译
  • 优化 SourceMap
  • 构建结果输出分析
  • Vue 项目的编译优化
    三、基础的 Web 技术的优化
    ① 开启 gzip 压缩
    ② 浏览器缓存
    ③ CDN 的使用
    ④ 使用 Chrome Performance 查找性能瓶颈

————————————————————————————

深入响应式原理
1、如何追踪变化?
vue 会把实例中data中的对象的每个property遍历出来,通过Object.defineProperty 把这些 property 全部转换为 getter/setter。
而每个组件实例都有一个 watcher实例,组件渲染过程中会把接触过的property记录为依赖。当依赖项的setter触发时,会通知watcher,使关联的组件重新渲染。

2、vue不能检测数组和对象的变化
Vue 无法检测 property 的添加或移除。由于 Vue 会在初始化实例时对 property 执行 getter/setter 转化,所以 property 必须在 data 对象上存在才能让 Vue 将它转换为响应式的。
要使用 Vue.set(…,…) 或 vm. s e t ( . . . . . , . . . . . ) 向 嵌 套 对 象 添 加 响 应 式 的 p r o p e r t y 。 数 组 : V u e . s e t ( v m . i t e m s , i n d e x O f I t e m , n e w V a l u e ) 或 v m . set(.....,.....) 向嵌套对象添加响应式的 property。 数组:Vue.set(vm.items, indexOfItem, newValue) 或 vm. set(.....,.....)propertyVue.set(vm.items,indexOfItem,newValue)vm.set(vm.items, indexOfItem, newValue) 或 vm.items.splice(indexOfItem, 1, newValue)
对象:Vue.set(object, propertyName, value)

虚拟dom 及其 实现原理
通过新旧DOM 节点的对比,获取对比后的差异,有针对性的把差异的部分渲染到对应的DOM 节点上,从而减少实际DOM操作,达到优化的目的。
虚拟DOM在Vue.js主要做了两件事:
① 提供与真实DOM节点所对应的虚拟节点vnode
② 将虚拟节点vnode和旧虚拟节点oldVnode进行对比,然后更新视图

组件怎么写?
组件要低耦合;
底层组件要是 无状态的;
顶层组件要 提供各个组件间的逻辑和业务联系;
因此分为 无状态的UI组件 + 业务组件。
(在满足低耦合情况下,实现功能的最小组件。)

history模式 和 hash模式 的区别?如何将 hash模式 变成 history模式。
vue-router 中有 hash 和 history 两种模式。
vue 的路由配置中有mode选项,最直观的区别在 hash 模式下 url 夹杂着“#”,history 模式没有。vue 默认使用 hash。
mode:“hash” / mode:“history”
hash模式依靠 onhashchange()事件去监听 location.hash 的改变。hash的值为#…;对服务器没有影响,改变hash不会重新加载页面。
history模式利用了 pushState()和 replaceState()方法。不怕前进,不怕后退,就怕刷新、f5,因为刷新是实实在在去请求服务器。若服务器没有相应的响应或资源,则会刷新出404页面。

简述 scrollBehavior (to, from, savedPosition) { } 第三个参数的作用和用法。
作用:切换到新路由时,页面滚动到期望滚动到的位置。
用法:savedPosition 仅在通过浏览器的 前进/后退 按钮触发时才可用。
返回滚动位置的对象信息——{x:number,y:number}

返回 savedPosition,在按下 后退/前进 按钮时,就会像浏览器的原生表现那样:
scrollBehavior (to, from, savedPosition) {
if (savedPosition) {
return savedPosition
} else {
return { x: 0, y: 0 }
}
}
②模拟“滚动到锚点”的行为:
scrollBehavior (to, from, savedPosition) {
if (to.hash) {
return {
selector: to.hash
}
}
}

vue-cli脚手架中dev.env.js和prod.env.js的作用
开发环境的变量
生产环境的变量
解决不同命令下项目启动和打包到指定的环境

vue开发中一些常见问题——————————————————
安装一些需要编译的包:提示没有安装python、build失败等
window-build-tools
pthon 2.x

can’t not find ‘xxModule’ - 找不到某些依赖或者模块
一般报错信息可以看到是哪个包抛出的信息.
卸载这个模块,安装重新安装即可.

data functions should return an object
vue实例中,单组件的data必须返回一个对象。
因为组件会重复调用,data 若还是一个对象,则所有实例将共享引用同一个数据对象。

我给组件内的原生控件添加事件,怎么不生效了!!!
要加 .native

我用了 axios , 为什么 IE 浏览器不识别(IE9+)
因为 IE 整个家族都不支持 promise
npm install es6-promise
require(“es6-promise”).polyfill();

我在函数内用了this.xxx=,为什么抛出Cannot set property ‘xxx’ of undefined;
this是和当前运行的上下文绑定。
在 axios 或 promise , 或 setInterval 默认都指向最外层的全局钩子。
简单点说:“最外层的上下文就是 window,vue内则是 Vue 对象而不是实例!”。
解决方案:
① 暂存法: 函数内先缓存 this , let that = this;(let是 es6, es5用 var)
② 箭头函数: 会强行关联当前运行区域为 this 的上下文。

我看一些Vue教程有这么些写法,是什么意思@click.prevent,v-demo.a.b;
@click.prevent:事件 + 修饰符。点击但又阻止默认行为
v-demo.a.b:自定义指令 + 修饰符。修饰符作用大多是给事件增加一些确切的拓展功能。

为什么我的引入的小图片渲染出来却是 data:image/png;base64xxxxxxxx
在 webpack 里面对应的插件处理。
小于多少k的图片直接转为 base64 格式渲染。
具体配置在 webpack.base.conf.js 里面的 rules 里面的 url-loader。
这样做的好处:在网速不好时 限制 内容加载 和 http 请求次数 来减少网站服务器的负担。

路由模式改为history后,除了首次启动首页没报错,刷新访问路由都报错!
必须给对应的服务端配置查询的主页面。

我想拦截页面,或者在页面进来之前做一些事情,可以么?
导航守卫

TypeError: xxx is not a function
写法有问题

Uncaught ReferenceError: xxx is not define
实力内的 data 对应的变量没有声明

Error in render function:“Type Error: Cannot read property ‘xxx’ of undefined”
初始化姿势不对

Unexpected token: operator xxxxx
语法错误。基本是符号问题

npm run build之后不能直接访问
要在本地搭个服务器

CSSbackground引入图片打包后,访问路径错误
因为打包后图片在根目录下,而我们用的是相对路径。
若把图片丢到 assets 目录下,然后相对路径,打包后是正常的。

template可以有多个div元素(×)
每个模板中只能有一个根元素

猜你喜欢

转载自blog.csdn.net/weixin_37877794/article/details/114142652