最近在准备找工作,整理下被问到的面试题以及搜索到的题目,大概记录一下。(涉及到原理和代码的话,会在以后找时间进行补充和完善)
javascript
防抖和节流
防抖
对于高频率事件事件来说,在被触发指定时间后在执行,如果在此期间在此被触发的,则会重新计时,直到指定时间内不在触发,才会执行。
例如可以定义一个定时器,在事件被触发之后,将该事件放到定时器中,如果在1秒内,该事件又被触发了,则清除这个定时器,重新定义一个,放入点击事件。循环如此。一秒没没点击,则执行定时器内的方法。
节流
在指定时间内,无论触发了事件几次,都只能执行一次事件的回调。可以使用时间戳类计算时间差。
es6新特性
函数柯里化
如果一个函数接收多个参数,可以将其转化为先接收一个或者一部分参数,然后在返回一个方法,接收另一个或者一部分参数,最后返回执行结果。
其可以复用参数,节省代码,减少工作代码重复性。
深克隆和浅克隆
事件轮询
jquery链式的实现原理
内部的每一个函数都会返回this。
对回调函数的理解
回调函数是作为参数传给另一个函数的函数,然后通过在外部函数内部调用该回调函数以完成某种操作。
css
水平居中和垂直居中
行内元素和块级元素
小程序
小程序页面跳转传参
vue
Vue父组件和子组件声明周期函数顺序
加载渲染过程
- 父 beforeCreate
- 父 created
- 父 beforeMount
- 子 beforeCreate
- 子 created
- 子 beforeMount
- 子 mounted
- 父 mounted
子组件更新过程
- 父 beforeUpdate
- 子 beforeUpdate
- 子 updated
- 父 updated
父组件更新过程
- 父 beforeUpdate
- 父 updated
销毁过程
- 父 beforeDestory
- 子 beforeDestory
- 子 destoryed
- 父 destoryed
vue组件之间的传参
父子组件
props + $emit
父组件
<component-a @btnclick="handleChangeParentData"></component-a>
// 子组件
Vue.component('component-a', {
template: `
<button @click="childBtnClick">btnClick</button>
`,
methods: {
childBtnClick: function(){
// $emit 触发组件绑定的父组件方法
this.$emit('btnclick');
}
}
})
跨组件传参
provider + inject
- 一旦注入了某个数据,比如上面示例中的 foo,那这个组件中就不能再声明 foo 这个数据了,因为它已经被父级占有。
//祖先组件,提供数据foo
export default {
name: "grandfather",
provide(){
return{
foo:'halo'
}
},
}
// 后代组件
export default {
inject:['foo'],
}
- 也可以将provider绑定到最顶层的组件(如App)上,作为全局变量, 也可以返回this,这样在所有的子组件中都可以注入(inject)。
//app.vue
export default {
name: 'App',
provide(){
return{
app:this
}
},
data(){
return{
text:"it's hard to tell the night time from the day"
}
},
methods:{
say(){
console.log("Desperado, why don't you come to your senses?")
}
}
}
//其他所有子组件,需要全局变量的,只需要按需注入app即可
export default {
inject:['foo','app'],
mounted(){
console.log(this.app.text);//获取app中的变量
this.app.say();//可以执行app中的方法,变身为全局方法!
}
}
vue-router
vue-router的基本使用
- 安装 => npm install vue-router -S
- 在main.js中导入vue-router => import VueRouter from 'vue-router';
- 使用插件 => Vue.use(VueRouter);
- 创建路由对象并配置路由规则 => let router = new VueRouter({ routes: [ { path: 'home', component: Home }]})
- 将路由对象传进Vue实例 => new Vue({ el:'#app', router: router })
- 在app.vue中留一个页面插槽 =>
router-view></router-view>
// main.js
import Vue from 'vue';
import VueRouter from 'vue-router';
import Home from './pages/Home';
import Index from './pages/Index';
Vue.use(VueRouter);
let router = new VueRouter({
routes: [
{
path: '/home',
name: 'homePage',
component: Home,
},
{
path: '/index',
name: 'indexPage'
component: Index,
// 嵌套路由
children: [
{
path: '/tab1',
component: Tab1,
},
{
path: '/tab2',
component: Tab2,
}
]
}
]
});
new Vue({
el: '#app',
// 传入路由规则
router: router
});
// App.vue
<template>
{/* 路由占位 */}
<router-view></router-view>
</template>
// Index.vue
<template>
<div>
IndexPage
</div>
// 嵌套路由的占位
<router-view></router-view>
</template>
vue-router嵌套路由
- 路由配置 children
- 对应vue页面,添加
<router-link></router-link>
标签
vue-router参数传递
路由跳转方式
<router-link to="url"></router-link>
this.$router.push(url)
传参
-
使用query来传递
- 传值页面:this.$router.push({ path: '/home', query: { id: 100 } } )
- 取值页面: this.$route.query.id // 100
注意: 传值的时候是$router,取值的时候是$route
-
写在router-link中的to属性上
-
传值:通过path
<router-link to="{ path: '/home', query: { id: 100 }}" ></router-link>
也可以通过name
<router-link to="{ name: 'homePage', query: { id: 100 }}" ></router-link>
-
取值: this.$route.query.id
-
vue-router路由守卫
全局守卫
- beforeEach((to, from, next) => { next() })
- afterEach((to, from) => { ... })
- next可以传入一个false,终止页面跳转,或者传入一个地址,更改跳转。如果不调用,则也会终止跳转。下next同。
路由独享的守卫
- 配置路由规则时候声明
{
path: '/',
component: Home,
beforeEnter:(to, from, next ) => { next() }
}
组件内守卫
- beforeRouteEnter => 不能访问this。
- beforeRouteUpdate
- beforeRouteLeave
webpack
webpack包括那几个方面?
entry
output
loader
loader有两个属性:
test 属性,识别出哪些文件会被转换。
use 属性,定义出在进行转换时,应该使用哪个 loader。