vue基础整理

172 阅读5分钟

image.png

1. vue2.x 生命周期

1.1 系统自带有哪些?

IMG_0901.PNG 创建阶段

  • beforeCreate
  • created
  • beforeMount
  • mounted

运行阶段

  • beforeUpdate
  • updated

销毁阶段

  • beforeDestroy
  • destroyed

1.2 一旦进入组件或页面,会执行哪些生命周期,并且它们的顺序?(见上图)

  • 我们只需关注进入页面或组件,不进行任何操作,会执行哪些生命周期,并且它们的顺序?
  • beforeCreate
  • created
  • beforeMount
  • mounted

1.3 在哪个阶段有$el(dom节点),在哪个阶段有$data(data节点)

  • beforeCreate  都没有
  •  created  有 $data,无$el(即还没有dom节点)
  •  beforeMount 有$data,无$el
  •  mounted 都有(所以到了mounted中才有dom节点)

1.4 如果是加了keep-alive 会多了两个生命周期

  • activated被 keep-alive 缓存的组件激活时调用
  • deactivated被 keep-alive 缓存的组件失活时调用

1.5 如果是加了 keep-alive,第一次进入组件会执行哪些生命周期?

  • beforeCreate
  • created
  • beforeMount
  • mounted
  • activated

1.6 如果是加了 keep-alive,第二次进入组件会执行哪些生命周期后者第N次进入组件会执行哪些生命周期?

  • activated 只执行这一个生命周期

2. 谈谈你对 keep-alive的了解?

  • 是什么?

keep-alive是vue中的内置组件,能在组件切换过程中将状态保留在内存中,防止重复渲染DOM

  • 使用场景

可以少网络请求,如果当前组件数据量比较大,就可以节省网络请求 >> 提升用户体验

  • 举例

如果详情页面之间进行切换,就可以使用keep-alive进行缓存组件,防止同样的数据重复请求

3. v-if 和 v-show 的区别?

  • 实现原理不同:
  • v-if指令会动态创建或移除DOM元素,从而控制元素在页面上的显示与隐藏
  • v-show指令会动态为元素添加或移除 display:none样式,从而控制元素的显示与隐藏
  • 使用场景不同:
  • 初次加载或切换次数少 v-if 更好,页面不会做加载盒子
  • 频繁切换,v-show更好,显示和隐藏消耗性能更少

4. v-if 和 v-for 优先级

v-for的优先级要比 v-if 高

5. ref是什么?

来获取dom元素和组件的引用

<h1 ref="myh1"> ref</h1>
console.log(this.$ref.myh1)

6. nextTick是什么?

  • 是什么?
  • 获取数据更新后的dom内容
  • 如果你在数据改变之后的操作跟改变之后的DOM有关,那么就应该使用this.$nextTick()
  • 使用场景
场景一:点击按钮展示输入框并获取焦点
<template>
  <div>
    <!-- 场景二:点击按钮原本隐藏的输入框,显示出来,并获取焦点 -->
    <input type="text" v-show="isShow" ref="focusRef" />
    <button @click="showIpt">展示输入框并获取焦点</button>
  </div>
</template>

<script>
export default {
  name: 'TestDemo2',
  data() {
    return {
      isShow: false
    }
  },
  methods: {
    showIpt() {
      this.isShow = true
      // 即此时数据发生了变化,但是 input 输入框的 display 属性仍是 之前的 none 而不是最新的 block
      console.log(this.$refs.focusRef.style.display) // none
      // 没有报错,但是也没拿到焦点,因为 此时拿到的 display 是 none  input 输入框都隐藏了,怎么能拿到焦点呢?
      // this.$refs.focusRef.focus()
      this.$nextTick(() => {
        this.$refs.focusRef.focus()
      })
    }
  }
}
</script>

场景二:数据的增加和删除
  <div>
    <div>
      <ul>
        <li ref="liNode" v-for="(item, index) in liList" :key="index">
          {{ item }}
        </li>
      </ul>
    </div>
    <button @click="addOneData">增加一条数据</button>
    <b>当前li长度为===〉{{ currLiLenth }}</b>
  </div>
</template>

<script>
export default {
  data() {
    return {
      liList: ['java', 'js', 'c'],
      // liList 数组的长度,默认为 0
      currLiLenth: 0
    }
  },
  created() {
    this.currLiLenth = this.liList.length
  },
  methods: {
    //增加一条li数据
    addOneData() {
      // 点击按钮,向 liList 数组追加值
      this.liList.push(1)

      // // 得到最新长度的数组的值,这种方式有问题
      // this.currLiLenth = this.$refs.liNode.length
      // // 添加后一条数据,此时数组 length 应该为 4
      // // 但是结果为三,原因在与 data 数组中数据的更新没来及同步到 dom 结构上
      // console.log(this.$refs.liNode.length) // 3

      //使用nextTick进行更新dom,会在dom更新之后的下一次进行回调
      this.$nextTick(() => {
        this.currLiLenth = this.$refs.liNode.length
      })
    }
  }
}
</script>

7. scoped原理

  • 作用:让样式在本组件中生效,不影响其他组件
  • 原理:给节点新增自定义属性,然后css根据属性选择器添加样式

8. vue中如何做到样式穿透?

vue中针对不同的样式类型(css,less,scss)有不用的样式穿透方法。

  • css 使用 >>>
  • less 使用 /deep/
  • scss 使用 ::v-deep
1. css
<style scoped>
    >>> .c1 .c2{
        color: green !important;
    }
</style>
2. less
<style scoped lang="less">
    /deep/ .c1 .c2{
        color: green !important;
    }
</style>
3. scss
<style scoped lang=”scss“>
    ::v-deep .c1 .c2{
        color: green !important;
    }
</style>

9. vue组件之间如何传值通信?

9.1 父组件传值子组件

父组件向子组件共享数据需要使用自定义属性

image.png

9.2 子组件传值父组件

子组件向父组件共享数据使用自定义事件

image.png

9.3 兄弟组件之间的传值

vue2.x 中,兄弟组件之间数据共享的方案是 EventBus

image.png image.png

9.4 通过 vuex

10. computed、methods、watch 有什么区别?

  • methods: 方法表示一个具体的操作,主要是书写业务逻辑(没有缓存)
  • computed: 计算属性会缓存计算的结果,只有计算属性依赖的数据变化时,才会重新进行运算
  • watch VS computed
  • computed 侧重于监听多个值的变化,最终计算并返回一个新值

  • watch 侧重于监听单个数据的变化,最终执行特定的业务操作,不需要任何返回值(场景:检测用户名是否可用)

11. props 和 data 优先级谁高?

props--> methods--> data--> computed--> watch

12. Vuex相关的面试题

12.1 Vuex有哪些属性?

  • state 提供唯一的公共数据源,所有共享的数据都要统一放到 Store 的 state 中进行存储 (类似Vue中的data)
  • mutations 用于变更 Store中的数据 (类似 Vue 中的methods)
  • actions 用于处理异步任务(提交mutations的)
  • getters 类似于 Vue 中的计算属性
  • modules 把以上四个属性再细分,让仓库更好管理

12.2 Vuex是单向数据流还是双向数据流?

  • Vuex是单向数据流

12.3 Vuex的 mutations 和 actions 的区别?

  • mutations中的方法可以直接修改state数据,actions是异步执行mutations中的方法,所以它俩都可以改数据,区别是:mutations是执行同步操作,actions 是执行异步操作。

12.4 Vuex如何做持久化存储?(vuex数据是存在内存中的,当页面刷新时,state中的数据会丢失)

  • 使用localStorage自己写

  • 使用数据持久化 vuex-persistedstate 插件

13. Vue设置代理(通过代理转发解决跨域问题 )

在vue.config.js 中 设置 devServer.proxy
 devServer:{
    proxy:{
      '/api':{//表示拦截以/api开头的请求路径
        target:'http://(这里填你项目真实的后端地址)',
        changOrigin: true,//是否开启跨域
        pathRewrite:{
          '^/api':'' //重写api,把api变成空字符,因为我们真正请求的路径是没有api的
        }
      }
    }
  }
  // main.js 
  axios.defaults.baseURL = '/api'

14. 打包路径(当项目打包后,打开页面是空白的问题)

// 在 vue.cofig.js 中,设置如下代码
module.exports = {
  publicPath:'./'
}
// 2. vue 路由模式是 history || hash,前端如果是自己测试项目,改为 hash,才会完全展示页面
// 2.1 项目上线要求是 history 模式,如何做? 让后端做重定向

15. Vue 接口环境设置

16. v-model双向绑定原理(在Vue源码中体现的)

  • 通过 Object.defineProperty劫持数据发生的改变,如果数据发生了改变,触发update方法,进行更新节点内容,从而实现了数据双向绑定的原理

17. diff 算法开篇