0


【面试】前端面试八股文

一、JS

1、使用

(1)标签引用

<script>alert("Hello,World!");</script>

(2)文件引用

<scriptsrc="main.js"></script>

2、特点

  • 解释型语言:JS不需要被编译为机器码而是直接执行,开发轻松
  • 动态型语言:JS变量与任何值类型都不关联,都可以重新分配类型值
  • 弱类型语言:变量数据类型不确定,赋值后定义。当操作涉及不匹配的类型时,允许隐式转换
  • 基于原型的面向对象
  • 严格区分大小写

3、标识符

  • 标识符:指给变量、函数、属性或函数参数起名字
  • 要求: - 第一个字符必须是字母、下划线( _ )或美元符号( $ )- 其它字符可以是字母、下划线、美元符号或数字- 按照惯例,ECMAScript 标识符采用驼峰命名法- 标识符不能是关键字和保留字符

4、数据类型

(1)数据类型

  • 简单/基本数据类型:在存储变量中存储值本身,因此也叫值类型,存放到栈(空间)
    名称类型值String字符串型‘123’Number数值型123Boolean布尔型true/falseNullnull型空UndefinedUndefined型未定义SymbolSymbol型Symbol() 生成唯一值Bigint整数型大整数

  • 复杂数据类型:在存储变量中存储地址,因此也叫引用数据类型,存放到堆(空间) - 通过new关键字创建的对象(系统对象、自定义对象)
    名称类型值Object对象{ “key”:“value” }Array数组[…]Function函数fn()Date日期函数new Date()Math数学公式MathRegExp正则new RegExp(“正则表达式”, “匹配模式”)

    (2)类型判断

  • typeof obj:不适用复杂类型判断,多显示object

console.log(typeof"123")// string
console.log(typeof123)// number
console.log(typeoftrue)// boolean
console.log(typeofundefined)// undefined
console.log(typeofnull)// object => 所有值均32位,最低的3位表示数据类型,null全部为0,而object前三位是000
  • obj instanceof Object :不适用基本类型判断
console.log([1,2]instanceofArray)// true
console.log(function(){}instanceofFunction)// true
console.log({a:1}instanceofObject)// true
console.log(newDate()instanceofDate)// true
console.log(newRegExp()instanceofRegExp)// true
  • obj.constructor:直接找到元素的构造函数类型
const str ='111'const num =666const sym =Symbol(66)const arr =[1,2,3,5]const date =newDate()constfunc=function(){}const reg =newRegExp()const map =newMap()const set =newSet()// null和undefined没有constructor,obj.constructor => Object() { [native code] }

console.log(str.constructor === String)// true
console.log(num.constructor === Number)// true
console.log(sym.constructor === Symbol)// true
console.log(arr.constructor === Array)// true
console.log(date.constructor === Date)// true
console.log(func.constructor === Function)// true
console.log(reg.constructor === RegExp)// true
console.log(map.constructor === Map)// true
console.log(set.constructor === Set)// true
  • Object.prototype.toString.call(obj):最准确,推荐使用
Object.prototype.toString.call("")// "[object String]"Object.prototype.toString.call(123)// "[object Number]"Object.prototype.toString.call(true)// "[object Boolean]"Object.prototype.toString.call(null)// "[object Null]"Object.prototype.toString.call(undefined)// "[object Undefined]"Object.prototype.toString.call(Symbol())// "[object Symbol]"Object.prototype.toString.call(42n)// "[object BigInt]"Object.prototype.toString.call({a:1})// "[object Object]"Object.prototype.toString.call([1,2])// "[object Array]"Object.prototype.toString.call(newDate())// "[object Date]"Object.prototype.toString.call(function(){})// "[object Function]"

(3)类型转换

  • 类型转换:把数据类型的变量转换成需要的数据类型

  • 显示转换:根据逻辑需要对数据进行显示转换
    转换类型方法含义StringString(数据)转换为字符串变量.toString(进制)转换为对应进制字符串NumberNumber(数据)转换为数字parseInt(数据)只保留整数parseFloat(数据)可以保留小数BooleanBoolean(数据)转换为布尔值

  • 隐式转换:某些运算符被执行时,系统自动转换``````+:一元操作符转换成Number;任何数据和字符串相加结果都是字符串- * /:把数据转成数字类型
    转换类型原始数据类型转换后的值String数字类型'n'null'null'undefined'undefined'布尔类型true变'true',false变'false'Number空字符/null0非空字符串数字/NaN(有非数字)true/false1/0undefinedNaNNaNtypeof NaN => "number"BooleanString非空字符串为true,空字符串为falseNumber非零数字为true,0和NaN为falseObject任何对象为true,null为falseUndefined无true,Undefined为false

    运行环境
    

    对数据类型隐式转换的影响:很多内置函数期望传入的参数数据类型是固定的,如:alert(value)期望传入string类型参数,如果传入number或object等非string类型的数据,就会发生数据类型的隐式转换

5、深浅拷贝

(1)基本类型拷贝

  • 基本类型数据的值保存在栈中,对它进行拷贝时,为新变量开辟了新空间,数据互相不影响,不涉及深浅拷贝问题

(2)引用类型拷贝

  • 复杂数据类型存储在栈中的值是一个指针,指向存储对象的内存地址,涉及深浅拷贝问题 - 浅拷贝:仅复制指向某对象的指针,不复制对象本身,新旧对象共享同一块内存- 深拷贝:创造一个相同的对象,新旧对象不共享内存,修改新对象不会改到原对象
    类型与原数据是否指向同一对象第一层数据为基本数据类型原数据中包含子对象赋值是改变原数据改变原数据浅拷贝否不改变原数据改变原数据深拷贝否不改变原数据不改变原数据

    深拷贝方法

    • JSON:JSON.stringify(),JSON.parse()
    • Object.assign()
    • jQuery 方法 $.extend()
    • 递归

6、var let const

  • 相同点:声明变量
  • 不同点:
    类型varletconst作用域函数作用域块作用域块作用域变量提升是否否重复声明是否否全局声明变量为window对象属性是否否

    尽量避免使用var,优先使用const,未来会修改的变量使用let
    const必须初始化,声明时大写变量,不能修改变量声明的值,可以修改对象内部属性
    let无需初始化,不可以修改变量声明的值

7、箭头函数

  • 匿名:都是匿名函数,使用=>简化定义
  • this:箭头函数没有this,通过查找作用域链来确定this的值,无法改变this指向
  • new:不能作为构造函数使用,同样也没有new.target值和原型
  • arguments:箭头函数没有自己的arguments对象,可以访问外围函数的arguments对象或用rest参数…解决

适合与this无关的回调 :定时器、数组回调
不适合与this有关的回调: 事件回调 、对象的方法

8、原型和原型链

(1)构造函数

  • 定义:使用new关键字来创建对象的函数,首字母一般大写
  • 实例:通过构造函数和new创建出来的对象,所有函数都是Function()的实例
  • new 操作符调用构造函数的步骤 - 创建一个新对象- 将构造函数的作用域赋给新对象(因此this指向了这个新对象)- 执行构造函数中的代码(为这个新对象添加属性)- 返回新对象
functionPerson(name, age){this.name = name;this.age = age;this.species ='人类';this.say=function(){
        console.log("Hello");}}let per1 =newPerson('xiaoming',20);

(2)原型对象

  • 原型对象 - js中每个函数类型的数据,都有一个prototype属性,这个属性指向原型对象- 原型对象又有个constructor属性,指向它的构造函数- 作用:存放实例对象的公有属性和方法
  • 显式原型:利用prototype属性查找原型,是函数类型数据的属性
  • 隐式原型:利用__proto__属性查找原型,这个属性指向当前对象构造函数的原型对象,是对象类型数据的属性,可以在实例对象上使用在这里插入图片描述

(3)原型链

  • 原型链:又叫隐式原型链,如果某个对象查找属性,自己和原型对象上都没有,那就会继续往原型对象的原型对象上去找,由__proto__属性串联起来,尽头是Object.prototype,返回undefined在这里插入图片描述

9、作用域和作用域链

(1)作用域

  • 定义:规定变量和函数的可使用范围
  • 局部作用域:函数中可以访问
  • 全局作用域:全局中可以访问

(2)作用域链

  • 定义:各作用域的嵌套关系,如果自身作用域未声明该变量,则通过作用域链层层查找
  • 区别:类似原型链,但原型链中查找不到对象属性返回undefined;作用域链中查找不到属性抛出ReferenceError
  • 作用域嵌套 - 内部作用域有权访问外部作用域- 外部作用域无法访问内部作用域(闭包登场解决)- 兄弟作用域不可互相访问在这里插入图片描述

10、执行栈和执行上下文

(1)执行栈

  • 特点是先进后出
  • 当进入一个执行环境,就会创建出它的执行上下文,然后进行压栈;当程序执行完成时,它的执行上下文就会被销毁,进行弹栈
  • 栈底永远是全局环境的执行上下文,栈顶永远是正在执行函数的执行上下文
  • 只有浏览器关闭的时候全局执行上下文才会弹出

(2)执行上下文

  • 全局执行上下文 - 创建一个全局的window对象,规定this指向window,执行js的时候压入栈底,关闭浏览器的时候弹出
  • 函数执行上下文 - 每次函数调用时,都会新创建一个函数执行上下文- 执行上下文分为创建阶段和执行阶段 - 创建阶段:函数环境会创建变量对象:arguments对象(并赋值)、函数声明(并赋值)、变量声明(不赋值),函数表达式声明(不赋值);确定this指向;确定作用域- 执行阶段:变量赋值、函数表达式赋值,使变量对象编程活跃对象
  • eval执行上下文

11、闭包

(1)定义

  • 本质是函数嵌套函数

(2)作用

  • 优点 - 保护:保护函数内的变量安全,避免命名冲突- 保存:在内存中维持一个变量,可以做缓存不被垃圾回收机制回收- 降耗:匿名自执行函数可以减少内存消耗
  • 缺点 - 内存泄漏:被引用的私有变量不能被销毁,增大了内存消耗,可能导致内存泄漏;可以使用完变量后手动为它赋值null- 降低性能:由于闭包涉及跨域访问,所以会导致性能损失;可以通过把跨作用域变量存储在局部变量中,然后直接访问局部变量减轻对执行速度的影响

(3)应用

  • 设计模式中的单例模式
  • for循环中的保留i的操作
  • 防抖和节流
  • 函数柯里化

12、内存泄露和垃圾回收机制

(1)内存泄漏

  • 定义:不再用的内存没有被及时释放,导致该段内存无法被使用
  • 原因:已经无法通过js访问某对象,而垃圾回收机制却认为该对象还在被引用,因此不释放该对象
  • 影响:内存无法释放,积少成多,系统会越来越卡以至于崩溃

(2)垃圾回收机制

  • 背景:写代码时创建的基本类型、对象、函数等,都需要占内存。JS基本数据类型存储在栈内存,引用数据类型存储在堆内存,但引用数据类型会在栈内存中存储一个实际对象的引用(内存泄漏)
  • 定义:定期找出不可达的对象(变量设置为null),然后将其释放
  • 方法: - 标记清除法:分为标记和清除两个阶段,标记阶段需要从根节点遍历内存中的所有对象,并为可达的对象做上标记;清除阶段则把没有标记的对象(非可达对象)销毁 - 优点:实现简单- 缺点:内存碎片化;内存分配速度慢- 引用计数法:主要记录对象是否被其他对象引用,如果没有就被垃圾回收机制回收。策略是跟踪记录每个变量值被使用的次数,当变量值引用次数为0时,垃圾回收机制就会把它清理掉 - 优点:可以实现立即进行垃圾回收- 缺点: 需要计数器;无法解决循环引用时计数不为0无法回收的问题

13、JS 执行机制

  • 进程:系统进行资源分配和调度的一个独立单位,具有一定独立功能的程序关于某个数据集合上的一次运行活动,可以粗俗的理解为主(大)任务
  • 线程:安排CPU执行的最小单位,可以理解为子任务 - 关系:线程可以视作为进程的子集,一个进程可以有多个线程并发执行- 区别:不同操作系统资源管理方式。进程有独立的地址空间,一个进程崩溃后,在保护模式下不会对其它进程产生影响;线程只是一个进程中的不同执行路径

(1)单线程

  • 背景:JS有可视DOM,多线程可能会导致不同线程同时增、删、改DOM节点,导致浏览器无法顺利执行
  • 定义:一次只能执行一段代码,执行时如果遇到耗时操作,默认停下等待操作完成后继续执行
  • 解决:JS一般把比较耗时的操作做异步处理

(2)同步和异步

  • 同步任务:在主线程上排队执行的任务。只有前一个任务执行完毕,才能执行下一个任务
  • 异步任务:进入任务队列的任务。只有任务队列通知主线程,某个异步任务可以执行了,该任务才会进入主线程
  • 事件循环: - 同步任务依次进入主线程并执行,形成一个执行栈- 异步任务进入任务队列并注册回调函数- 所有同步任务执行完毕,从任务队列中提取异步任务执行

异步任务分为宏任务和微任务,任务队列也分为宏任务队列和微任务队列:
宏任务:运行环境提供的异步操作,如:setTimeOut、setInternal、DOM监听、UI rendering、ajax、事件绑定等
微任务:js 语言自身的异步操作,如:Promise的then、catch、finally和process的nextTick等
在一个宏任务周期中会执行当前周期所有微任务,都执行完毕进入下一个宏任务周期,所以任务执行顺序为:同步任务>微任务>宏任务

14、回调函数

(1)定义

  • 函数也是一种变量,可以作为参数传给其他函数,在该外部函数中被调用以完成任务

(2)特点

  • 执行:不会立即执行,通过()运算符调用才会执行
  • 闭包:回调函数是一个闭包,能访问到其外层定义的变量
  • this:指向离它最近或嵌套级别的函数的调用者

解决回调函数this指向的方法:

  • 箭头函数
  • let self = this

(3)优点

  • 业务逻辑分离
  • 避免重复代码
  • 提高代码可维护性和可读性

(4)回调地狱

  • 定义:回调函数中嵌套回调函数
  • 目的:实现代码顺序执行
  • 缺点:造成代码可读性差,后期不好维护
setTimeout(function(){ 
   console.log('第一次打印');setTimeout(function(){
        console.log('第二次打印');setTimeout(function(){
            console.log('第三次打印');},1000)},2000)},3000)
  • 解决:Promise、async/await

15、Promise

(1)定义

  • Promise是异步编程的一种解决方案,本质是一个构造函数
  • Promise类似容器,保存着某个未来才会结束的事件(通常是一个异步操作)的结果
  • 从语法上说,Promise是一个对象,从它可以获取异步操作的消息
  • Promise提供统一的API,各种异步操作都可以用同样的方法进行处理

(2)特点

  • 对象的状态不受外界影响。Promise对象代表一个异步操作,有三种状态:pending(进行中)、fulfilled(已成功)和rejected(已失败)。只有异步操作的结果,可以决定当前是哪一种状态,任何其他操作都无法改变这个状态。这也是Promise这个名字的由来,它的英语意思就是“承诺”,表示其他手段无法改变
  • 一旦状态改变,就不会再变,任何时候都可以得到这个结果。Promise对象的状态改变,只有两种可能:从pending变为fulfilled和从pending变为rejected。只要这两种情况发生,状态就凝固了,不会再变了,会一直保持这个结果,这时就称为 resolved(已定型)。如果改变已经发生了,你再对Promise对象添加回调函数,也会立即得到这个结果。这与事件(Event)完全不同,事件的特点是,如果你错过了它,再去监听,是得不到结果的

(3)优缺点

  • 优点: - 可以将异步操作以同步操作的流程表达出来,避免了层层嵌套的回调函数- Promise对象提供统一的接口,使得控制异步操作更加容易。
  • 缺点: - 无法取消Promise,一旦新建就立即执行,无法中途取消- 如果不设置回调函数,Promise内部抛出的错误,不会反应到外部- 当处于pending状态时,无法得知目前进展到哪一个阶段(刚开始或将完成)

(4)基本用法

  • new Promise调用构造函数,其参数是一个函数,该函数的两个参数分别又是两个函数reslove和reject
  • promise对象自带两个方法then和catch,这两个方法中会分别再传入一个回调函数,返回所需成功或失败的信息 - then方法返回的是一个新的Promise实例,因此可以采用链式写法,即then方法后面再调用另一个then方法- catch方法调用指定发生错误时的回调函数
const promise =newPromise((resolve,reject)=>{//异步代码setTimeout(()=>{// resolve(['111','222','333'])reject('error')},2000)})
promise.then((res)=>{
    console.log('success',res)// success}).catch((err)=>{
    console.log('fail',err)// error})
    • promise对象自带finally方法用于指定不管 Promise 对象最后状态如何,都会执行的操作,本质是then方法的特例
promise
.then(result=>{···}).catch(error=>{···}).finally(()=>{···});
  • all方法用于将多个 Promise 实例,包装成一个新的 Promise 实例
const databasePromise =connectDatabase();const booksPromise = databasePromise.then(findAllBooks);const userPromise = databasePromise.then(getCurrentUser);

Promise.all([
  booksPromise,
  userPromise
]).then(([books, user])=>pickTopRecommendations(books, user))

16、async/await

  • async/await 是对 Promise 的升级,用同步的方法写异步的代码
  • async用于声明一个函数是异步的,await是等待一个异步方法执行完成

(1)async

  • 作为一个关键字放到声明函数前面,表示该函数为异步任务,不会阻塞后面函数的执行
  • 返回数据时自动封装为一个Promise对象

(2)await

  • 不能单独使用,只能在使用async定义的函数中使用
  • ​后面可以直接跟一个 Promise实例对象
  • 可以直接拿到Promise中resolve中的数据

17、改变this指向(call、apply、bind)

(1)this

  • 普通函数:谁调用,this指向谁
  • 箭头函数:箭头函数没有this,使用父作用域的this

普通函数:没有调用者,this默认指向window
箭头函数:外面如果被函数包裹,this指向外包裹函数;如果没有外包裹函数,this指向window

(2)改变this指向的三个方法

  • call(this指向对象, 参数列表)
let obj1 ={name:'james',getName1:function(a,b,c){
            console.log(`getName ${this.name}`);// getName davis
            console.log(`参数:${a},${b},${c}`);// 参数:1,2,3}}let obj2 ={name:'davis',getName2:function(){
            console.log(`getName ${this.name}`);}}
 obj1.getName1.call(obj2)
 obj1.getName1.call(obj2,1,2,3)

call 执行函数,并改变this指向为函数的第一个参数,临时改变一次this指向,立即执行
call 可以传入多个参数

  • apply(this指向对象, 参数数组)
let obj1 ={name:'james',getName1:function(a,b,c){
        console.log(`getName ${this.name}`);// getName davis
        console.log(`参数:${a},${b},${c}`);// 参数:1,2,3}}let obj2 ={name:'davis',getName2:function(){
        console.log(`getName ${this.name}`);}}
obj1.getName1.apply(obj2,[1,2,3])

apply 执行函数,并改变this指向为函数的第一个参数,临时改变一次this指向,立即执行
apply 只能传入两个参数,第二个参数只能是

数组

的形式

  • bind(this指向对象, 参数列表)
let obj1 ={name:'james',getName1:function(a,b,c){
        console.log(`getName ${this.name}`);// getName davis
        console.log(`参数:${a},${b},${c}`);// 参数:1,2,3}}let obj2 ={name:'davis',getName2:function(){
        console.log(`getName ${this.name}`);}}let fn = obj1.getName1.bind(obj2,1,2,3)fn()

bind 改变this指向为第一个参数,但是不会自动执行函数,返回一个永久改变this指向的函数,需要时调用
bind 可以传入多个参数

18、继承

(1)背景

  • 在实际编码过程中,很多类似方法存放于构造函数中,会导致内存浪费(内存泄漏),此时可以用继承解决

(2)定义

  • 继承就是通过某种方式让一个对象可以访问另一个对象中的属性和方法

(3)方式

  • 原型链继承:将父类的实例作为子类的原型
  • 构造继承:使用父类的构造函数来增强子类实例,等于是复制父类的实例属性给子类(没用到原型)
  • 实例继承:为父类实例添加新特性,作为子类实例返回
  • 组合继承:通过调用父类构造,继承父类的属性并保留传参的优点,然后通过将父类实例作为子类原型,实现函数复用
  • 寄生组合继承:通过寄生方式,砍掉父类的实例属性,这样在调用两次父类的构造的时,不会初始化两次实例方法/属性,避免组合继承的缺点在这里插入图片描述

19、防抖和节流

  • 防抖:触发事件后n秒内只执行一次函数,若在n秒内重复触发,则重新计时
functiondebounce(fn, delay){let timerId =nullreturnfunction(){const context =thisif(timerId){window.clearTimeout(timerId)}
        timerId =setTimeout(()=>{fn.apply(context, arguments)
            timerId =null},delay)}}
  • 节流:连续触发事件但n秒内只执行一次函数,稀释函数的执行频率
functionthrottle(fn, delay){let canUse =truereturnfunction(){if(canUse){fn.apply(this, arguments)
            canUse =falsesetTimeout(()=>canUse =true, delay)}}}

20、BOM/DOM

(1)常用的 BOM 对象和方法

BOM 对象和方法含义alert(“提示”)提示信息confirm(“确认”)确认信息prompt(“输入”)弹出输入框open(“url”,“black/self”,“新窗口大小”)打开网页close()关闭当前网页

(2)常见的 DOM 元素选择方式

DOM 元素选择方式含义getElementById通过ID获取getElementsByClassName通过类名获取getElementsByTagName通过标签名获取document.documentElement获取 htmldocument.body获取 bodyquerySelector通过选择器获取一个元素(开发常用)querySelectorAll通过选择器获取一组元素(开发常用)

二、HTML/CSS

1、标签

(1)块级元素(display:block)

  • 块级元素独占一行
  • 宽度默认是容器的 100%
  • 宽、高,内、外边距都可以单独设置
  • 可以容纳内联元素和其他块级元素 > div 、p、h1~h6、hr> 表单:form、fieldset、legend> 列表:ul、ol、li、dl、dt、dd> 表格:table、caption、thead、tbody、tfoot、th、tr、td> 语义化标签:header、footer、main、nav、section、article、pre

(2)行内元素(display:inline)

  • 和相邻的行内元素在一行
  • 默认的宽度就是本身内容的宽度
  • 宽、高无效,但是水平方向上的内外边距可以设置,垂直方向无效
  • 行内元素只能容纳纯文本或其他行内元素(a 标签除外) > a、span、abbr、small、b、strong、em、br、cite、i、code、label、q、select、sub、sup、textarea、var

(3)行内块元素(display:inline-block)

  • 和相邻的行内(块)元素在一行,中间有空白间隙

  • 默认的宽度就是本身内容的宽度

  • 宽、高,内、外边距都可以设置

  • 通过 inline-block、浮动、绝对定位、固定定位转化过来 > img、input
    标签类型排列方式宽高边距设置默认宽度块级元素独占一行均可单独设置容器的100%行内元素与相邻行内元素在一行宽、高无效,
    水平方向上的内外边距可以设置,垂直方向无效自身内容的宽度行内块元素与相邻的行内(块)元素在一行,
    中间有空白间隙均可单独设置自身内容的宽度

    2、盒模型

    名称含义width宽度height高度padding元素内容与元素边框距离(填充)margin元素边框间距(盒子间距)

  • 外边距合并:标准文档流中,块级元素 margin 在垂直方向出现叠加现象,大值覆盖小值 - 兄弟盒子:相邻块级元素垂直外边距取大值 > 只给同级元素中的一个元素设置 margin-top/bottom> 给每一个元素添加父元素,然后触发 BFC 规则(不推荐)- 父子盒子:嵌套块级元素垂直外边距子带父 > 使用伪元素 ::before,::after> 触发 BFC (overflow、float、display、position)> 给父元素设置 margin、padding (不推荐)

(1)标准盒模型(content-box)

  • 设置的 width 与 height 只包括内容的宽、高, 不含边框和内外边距
  • 尺寸计算公式:

盒子实际宽度 = border _ 2 + padding _ 2 + 内容宽度(width)
盒子实际高度 = border _ 2 + padding _ 2 + 内容高度(height)

标准盒模型

(2)怪异盒模型(border-box)

  • 设置的 width 与 height 包括内容的宽、高、边框、内边距,不含外边距
  • 尺寸计算公式: > 盒子实际宽度 = width = border _ 2 + padding _ 2 + 内容宽度> 盒子实际高度 = height = border _ 2 + padding _ 2 + 内容高度

怪异盒模型

3、浮动与清浮动

(1)浮动

  • 元素 float 脱离文档流移动(left/right),直到外边缘碰到包含框或另一个浮动框位置

(2)清浮动

  • 清除浮动元素导致的高度塌陷,使页面布局正常显示

(1)添加高度:父元素添加 height/border/padding
(2)额外标签:浮动元素后添加一个空块级元素含属性 clear:both
(3)单伪元素:父元素添加 .clearfix::after{content:‘’; display:block;clear:both}
(4)双伪元素:父元素添加 .clearfix::after,.clearfix::before // 顺便清除外边距塌陷
(5)overflow :父元素添加 overflow:hidden

  • 常用清浮动配置
.clearfix::after{content:'';display: block;height:0;clear: both;visibility: hidden;}

4、选择器

(1)基本选择器

基本选择器使用通配符统一调配所有属性,用

*

调用class元素中定义 class 属性,用

.类名

调用id元素中定义id属性,用

#id名

调用element用

标签名

调用群组同时选择

多个类名,逗号隔开

(2)层次选择器

层次选择器使用包含/后代元素被包含在前一个元素内,选择此父元素内所有后代,用

父元素 后代元素

调用子匹配元素的孩子,用

父元素 > 子元素

调用相邻兄弟修改兄元素后第一个紧邻的弟元素样式,用

兄元素 + 弟元素

调用通用兄弟修改兄元素后所有弟元素样式,用

兄元素 ~ 弟元素

调用

(3)伪类选择器

  • 链接伪类
    链接伪类含义a:link未访问a:visited访问后a:hover悬停时a:avtive点击时

  • 目标伪类 - URL 通过锚点 #id 指向页面特定元素- 用 :target 调用
    目标伪类含义

    <a href="#id">操作者</a>
    

    事件触发对象

    <p id="id">指向者</p>
    

    事件实施对象#id:target{}点击操作者时,改变样式

  • UI元素状态伪类
    UI元素状态伪类含义E:hover匹配当鼠标指针移动到元素上时,改变样式E:active匹配元素被激活时,改变样式E:focus匹配表单元素获取焦点,改变样式E:enabled匹配所有启用的表单元素,改变样式E:disabled匹配所有禁用的表单元素,改变禁用状态下的样式E:checked匹配的是复选或者单选按钮的表单元素,点击之后的样式

  • 结构伪类
    结构伪类含义E:first-child用来定位一组兄弟元素中的第一个元素E:last-child用来定位一组兄弟元素中的最后一个元素E:nth-child(n)用来定位一组兄弟元素中的第n个元素E:nth-last-child(n)用来定位一组兄弟元素中倒序方式的第n个元素E:first-of-type用来定位一组同类型的兄弟元素中的第一个元素E:last-of-type用来定位一组同类型的兄弟元素中的最后一个元素E:nth-of-type(n)用来定位一组同类型的兄弟元素中的第n个元素E:nth-last-of-type(n)用来定位一组同类型的兄弟元素中倒序方式的第n个元素E:only-child用来定位一个没有任何兄弟元素的元素E:only-of-type用来定位一个没有任何同类型兄弟元素的元素E:empty用来定位一个没有子级元素的元素,并且该元素也没有任何文本内容E:root用来定位 HTML 页面中的根元素(html)E:first-letter定义指定元素首字母E:first-line定义指定元素首行E:selection定义被用户选取的部分(修改字体/背景颜色)

  • 否定伪类
    否定伪类含义E:not(F)匹配E元素中所有除了F以外的元素

    (4)伪元素

    伪元素含义E::aftercontent 在元素之后显示E::beforecontent 在元素之前显示E::first-letter定义指定元素首字母E::first-line定义指定元素首行E::selection定义被用户选取的部分(修改字体/背景颜色)

    (5)属性值匹配

    属性值含义E[attr]包含

    指定属性
    

    的元素[attr = “val”]包含

    完全匹配属性值
    

    的元素,如英语(美式) [lang = “en-us”][attr = val]包含

    起始片段完全匹配
    

    的元素,起始值正好是 val 或外加短横线 - 开头,如英语(美式/英式) [lang = en][attr ~ = val]包含

    属性值字符
    

    的元素,val 单独存在或与其他属性值空格隔开[attr * = val]包含

     val 片段
    

    的元素[attr ^ = val]包含

    位于起始的 val 片段
    

    的元素[attr $ = val]包含

    位于末端的 val 片段
    

    的元素

    5、css 优先级

    选择器优先级important!无条件优先内联样式1000id选择器100class、伪类、属性10标签伪元素1

    6、常见布局方式

常见布局

(1)float

  • 特点:元素脱离了文档流,使父容器的高度塌陷,但是不脱离文本流
    float含义none默认无浮动left左浮动right右浮动

  • 解决:清浮动 - 父级添加 overflow : hidden- 父级添加 clearfix(推荐)

// 给父级元素添加了一个 ::after 伪元素,通过清除伪元素的浮动,达到撑起父元素高度的目的.clearfix::after{content:'';display: block;height:0;clear: both;visibility: hidden;}
    • 浮动元素后添加空标签(不推荐)
<div style="clear: both"></div>// 易造成结构混乱,不利于后期维护

(2)position

  • 特点:可以精准定位页面中的任意元素
  • 设置非 static 定位以后,可以设置 left、right、top、bottom
    position类型含义参照系是否脱标(不占位)static静态定位元素默认定位标准流否relative相对定位元素相对自身位置定位
    自身
    
    否absolute绝对定位元素相对非静态父级定位
    子绝父相最近的
    非static祖先元素
    
    是fixed固定定位元素相对浏览器窗口定位
    浏览器窗口
    

    网页布局总结:
    层级:标准流(海底) ==> 浮动盒子(陆地) ==> 定位盒子(天空)
    区别:
    ① 标准流:块盒子上下排列
    ② 浮动:块盒子左右排列
    ③ 定位:盒子堆叠,默认后来居上,z-index 值调整堆叠顺序

(3)flex

  • 决定大盒子(display:flex)中的小盒子如何分布、排列,创建自适应浏览器窗口的弹性布局

  • flex 属性
    flex盒子属性含义flex-direction主轴方向flex-wrap换行flex-flow前两条简写形式justify-content主轴对齐方式align-items侧轴对齐方式align-content多根轴线对齐方式

    • 主轴对齐
      justify-content含义flex-start当前行的最左边flex-end当前行的最右边center当前行的中间位置space-between间距相等排列,两边不留白space-around间距相等排列,两边留白间距一半space-evenly间距相等排列,两边留白也相等
    • 侧轴对齐
      align-items含义flex-start当前行的最左边flex-end当前行的最右边center当前行的中间位置stretch子元素未设置高度或 auto,占满容器高度baseline以子元素第一行文字的基线对齐
  • 项目属性
    项目盒子含义order项目的排列顺序,数值越小排列越靠前,默认为0flex-grow项目的放大比例,默认为0flex-shrink项目的缩小比例,默认为1flex-basis主轴是否有多余空间flex前三者简写,默认为0 1 autoalign-self单个项目个性对齐方式

    (4)grid

  • 特点:目前唯一一种 CSS 二维布局

  • 网格单元:小格子,网格元素中最小的单位

  • 网格线:划分网格的线,定义的是网格轨道
    代码类型含义display:grid/inline-grid创建网格容器使其直系子元素成为网格项目grid-template-columns设置列设置

    列宽
    

    和数量(repeat())grid-template-rows设置行设置

    行高
    

    和数量(repeat())grid-gap设置行间距和列间距grid-row-gap与grid-column-gap的简写

    (5)table

父级容器 - display:table
子级容器 - display:table-cell

(6)BFC

  • 定义:BFC(Block Formatting Context),块级格式化上下文

  • 特点:独立的布局空间,内部子元素不影响外部标签
    触发条件触发值根元素htmlfloatleft、right、inheritpositionabsolute、fixedoverflowhidden、auto、scrolldisplayflex、inline-flex、grid、inline-block、table-cell

  • 用途: - 自适应两栏布局- 清除内部浮动- 阻止元素被浮动覆盖- 阻止 margin 重叠- 解决高度塌陷问题

高度塌陷:父元素自适应高度,子元素浮动后脱标(脱离标准流),父元素高度为 0

7、度量单位

度量单位含义px像素em相对于父元素字体大小rem相对根元素字体大小vw相对于视口的宽度,1vw 等于视口宽度的1%(总视口宽度为100vw)vh相对于视口的高度,1vh 等于视口高度的1%(总视口高度为100vh)rpx小程序独有,把所有设备的屏幕,在宽度上等分为750份(即当前总宽度为750rpx)

8、HTML5/CSS3 新特性

(1)语义化标签

  • 代码结构:使页面没有css的情况下,也能够呈现出很好的内容结构
  • 有利于SEO:爬虫依赖标签来确定关键字的权重,因此可以和搜索引擎建立良好的沟通,帮助爬虫抓取更多的有效信息
  • 提升用户体验:例如title、alt可以用于解释名称或者解释图片信息,以及label标签的灵活运用
  • 便于团队开发和维护:语义化使得代码更具有可读性,让其他开发人员更加理解你的html结构,减少差异化
  • 方便其他设备解析:如屏幕阅读器、盲人阅读器、移动设备等,以有意义的方式来渲染网页

(2)增强型表单

  • 增加 type 类型:color、date、datetime、datetime-local、email、month、number、range、search、tel、time 等

在这里插入图片描述

  • 增加 select 元素(下拉选框)、textarea 元素(文本域)、button 元素(按钮)、datalist 元素(预定义选项列表)

(3)媒体元素

  • audio:音频
  • video:视频

(4)canvas 绘图

  • canvas 是画布,可以绘制复杂图形、做动画、处理图像、开发游戏、处理视频,支持二维矢量绘图、三维绘图
  • canvas 元素本身没有绘图能力,绘制工作通过 JS 调用 getContext(‘2d’)完成

绘制直线:
beginPath():开始绘图路径
moveTo():将坐标移至直线起点
lineTo():绘制直线
stroke():图形的边界轮廓
closePath():闭合绘图路径

绘制矩形:
rect(x,y,width,height):绘制矩形
strokeRect(x, y, width, height):矩形边框
fillRect(x, y, width, height):填充矩形
clearRect(x, y, width, height):擦除指定矩形区域

绘制圆弧:
arc(centerx,centery,radius,startAngle,endAngle,antiClockwise);
centerx,centery:圆弧中心点坐标
Radius:半径
startAngle:起始弧度
endAngle:终止弧度
antiClockwise:是否按逆时针方向绘图(可选参数)默认为false
弧度 = 角度* ( Math.PI / 180 )

填充和描边
strokeStyle:描边颜色(三种颜色方式均可)
lineWidth:描边宽度(单位:像素)
fillStyle:填充颜色(三种颜色方式均可)

(5)svg 绘图(可伸缩矢量图)

(6)地理定位

  • 使用 getCurrentPosition() 方法来获取用户的位置,从而实现队地理位置的定位

(7)拖放API

(8)Web Worker

  • worker 加载脚本文件 => 创建独立工作线程(主线程之外运行) => worker 线程运行结束把结果返回给主线程(处理计算密集型任务,优化主线程) =>浏览器提供JS多线程运行的宿主环境

(9)Web Storage

  • 掌握 cookie、Localstorage、 SessionStorage 三者区别
    Web Storage数据生命周期存放数据大小与服务器端通信易用性Cookie可设置失效时间,默认是关闭浏览器后失效4K左右每次都会携带在HTTP头中,如果使用cookie保存过多数据会带来性能问题原生Cookie接口不友好,需要程序员自己封装localStorage除非被清除,否则永久保存5MB左右仅在客户端保存,不参与和服务器的通信原生接口可以接受,也可以再次封装sessionStorage仅在当前会话下有效关闭页面或浏览器后被清除5MB左右仅在客户端保存,不参与和服务器的通信原生接口可以接受,也可以再次封装

    (10)Websocket

  • 掌握 websocket 和 HTTP 的区别 - 相同点:HTTP 和 Websocket 都是基于TCP的应用层协议- 不同点: - websocket 是双向通信协议,模拟socket协议,可以双向发送和接受消息;HTTP 是单向的,通信只能由客户端发起。- websocket 是需要浏览器和服务器通过握手建立连接,HTTP 是浏览器向服务器发送连接,服务器预先不知道这个连接。- 联系:websocket 建立握手时需要基于 HTTP 进行传输,建立连接之后不再需要HTTP协议

(11)选择器

(12)边框与圆角

border-radius:水平半径/垂直半径
四个值:左上/右上/右下/左下
三个值:左上/右上和左下/右下
两个值:左上和右下/右上和左下
一个值:4角生效

(13)rgba

  • rgba(r, g, b, a);

(14)盒子

  • box-shadow: cx cy 模糊程度 扩展程度 颜色 内阴影;
  • box-sizing:border-box;

(15)背景与渐变

  • background:color position size repeat origin clip attachment image;
  • background-image: linear-gradient(to方向/deg, color1 , color2);

(16)过渡

  • transition:property duration timing-function delay;

(17)变换

  • transform: - 2D:rotate(deg) translate() scale() skew(deg);- 3D: - 开启:transform-style: preserve-3d;- 景深:perspective: px;

(18)动画

  • animation:animationname,duration,timing-function,delay,count,direction(默认normal),play-state(默认running)
@keyframes  animationname{
  keyframes-selector{
  cssStyles;}

三、计算机网络

1、HTTP 报文

  • 组成:请求/响应行、请求/响应头、请求/响应体在这里插入图片描述

2、常见状态码

(1)状态码类型

状态码类别原因短语1xxInformation(信息状态码)接受的请求正在处理2xxSuccess(成功状态码)请求正常处理完毕3xxRedirection(重定向状态码)需要进行附加操作以完成请求4xxClient Error(客户端错误状态码)服务器无法处理请求5xxServer Error(服务端错误状态码)服务器处理请求出错

(2)常见状态码

1xx信息状态码100(继续) 接受的请求正在处理2xx****成功状态码

200

(成功) 服务器已成功处理请求,服务器提供了请求网页201(已创建) 请求成功并且服务器创建了新的资源202(已接受) 服务器已接受请求,但尚未处理3xx****重定向状态码300(多种选择) 表示要完成请求,需要进一步操作,通常用来重定向

301

(永久移动) 资源已被分配了新的 URL

302

(临时移动) 资源临时被分配了新的 URL303(查看其他位置) 表示资源存在另一个URL,用GET方法获取资源304(未修改) 自从上次请求后,请求网页未修改过。服务器返回此响应时,不会返回网页内容4xx****客户端错误状态码

400

(错误请求) 服务器不理解请求的语法

401

(未授权) 发送的请求需要

身份验证

,可能需要登录

403

(禁止) 服务器拒绝请求

404

(未找到) 服务器找不到请求的网页5xx****服务端错误状态码

500

(服务器内部错误) 服务器遇到错误,无法完成请求501(尚未实施) 服务器不具备完成请求的功能502(错误网关) 服务器作为网关或代理,从上游服务器收到无效响应

503

(服务不可用) 服务器目前无法使用(由于超载或停机维护)

3、TCP 三次握手/四次挥手

  • UDP:在传送数据前不需要建立连接,远地的主机在收到UDP报文后也不需要确认。虽然UDP不提供可靠交付,但因此省去很多的开销,使它的速度较快。实时性要求较高的服务,常使用UDP。对应的应用层的协议主要有 DNS、TFTP、DHCP、SNMP、NFS 等
  • TCP:提供面向连接的服务,在传送数据之前必须先建立连接,数据传送完成后要释放连接。因此TCP是一种可靠的运输服务,但因此增加了许多开销,比如确认,流量控制等。对应的应用层的协议主要有 SMTP、TELNET、HTTP、FTP 等

(1)TCP连接的建立(三次握手)

  • 最开始客户端和服务器都处于CLOSED状态。主动打开连接的为客户端,被动打开连接的是服务器

  • TCP服务器进程先创建传输控制块TCB,时刻准备接受客户进程的连接请求,此时服务器就进入了LISTEN(监听)状态
  • TCP客户进程也是先创建传输控制块TCB,然后向服务器发出连接请求报文,这是报文首部中的同部位SYN=1,同时选择一个初始序列号 seq=x ,此时,TCP客户端进程进入了 SYN-SENT(同步已发送状态)状态。TCP规定,SYN报文段(SYN=1的报文段)不能携带数据,但需要消耗掉一个序号
  • TCP服务器收到请求报文后,如果同意连接,则发出确认报文。确认报文中应该 ACK=1,SYN=1,确认号是ack=x+1,同时也要为自己初始化一个序列号 seq=y,此时,TCP服务器进程进入了SYN-RCVD(同步收到)状态。这个报文也不能携带数据,但是同样要消耗一个序号
  • TCP客户进程收到确认后,还要向服务器给出确认。确认报文的ACK=1,ack=y+1,自己的序列号seq=x+1,此时,TCP连接建立,客户端进入ESTABLISHED(已建立连接)状态。TCP规定,ACK报文段可以携带数据,但是如果不携带数据则不消耗序号
  • 当服务器收到客户端的确认后也进入ESTABLISHED状态,此后双方就可以开始通信了

(2)TCP连接的释放(四次挥手)

  • 数据传输完毕后,双方都可释放连接。最开始客户端和服务器都是处于ESTABLISHED状态,然后客户端主动关闭,服务器被动关闭在这里插入图片描述
  • 客户端进程发出连接释放报文,并且停止发送数据。释放数据报文首部,FIN=1,其序列号为seq=u(等于前面已经传送过来的数据的最后一个字节的序号加1),此时,客户端进入FIN-WAIT-1(终止等待1)状态。 TCP规定,FIN报文段即使不携带数据,也要消耗一个序号
  • 服务器收到连接释放报文,发出确认报文,ACK=1,ack=u+1,并且带上自己的序列号seq=v,此时,服务端就进入了CLOSE-WAIT(关闭等待)状态。TCP服务器通知高层的应用进程,客户端向服务器的方向就释放了,这时候处于半关闭状态,即客户端已经没有数据要发送了,但是服务器若发送数据,客户端依然要接受。这个状态还要持续一段时间,也就是整个CLOSE-WAIT状态持续的时间
  • 客户端收到服务器的确认请求后,此时,客户端就进入FIN-WAIT-2(终止等待2)状态,等待服务器发送连接释放报文(在这之前还需要接受服务器发送的最后的数据)。 服务器将最后的数据发送完毕后,就向客户端发送连接释放报文,FIN=1,ack=u+1,由于在半关闭状态,服务器很可能又发送了一些数据,假定此时的序列号为seq=w,此时,服务器就进入了LAST-ACK(最后确认)状态,等待客户端的确认
  • 客户端收到服务器的连接释放报文后,必须发出确认,ACK=1,ack=w+1,而自己的序列号是seq=u+1,此时,客户端就进入了TIME-WAIT(时间等待)状态。注意此时TCP连接还没有释放,必须经过2∗ *∗MSL(最长报文段寿命)的时间后,当客户端撤销相应的TCB后,才进入CLOSED状态
  • 服务器只要收到了客户端发出的确认,立即进入CLOSED状态。同样,撤销TCB后,就结束了这次的TCP连接。可以看到,服务器结束TCP连接的时间要比客户端早一些

4、网页从开始到加载的过程(输入url以后你的电脑淦了什么)

  • 输入网址后做域名解析: - 先查看本地hosts文件是否保存对应ip地址,若有直接发起请求- 未果从本地域名服务器查找- 未果从根域名服务器查找,查找到对应的ip地址后把对应规则保存到本地的hosts文件
  • 根据 ip 地址查到服务器:进行http请求,三次握手四次挥手建立断开连接
  • 服务器处理: - 返回304,协商缓存,直接使用客户端缓存即可- 返回200,同时返回对应的数据
  • 服务器返回数据,客户端自上而下执行代码: - CSS加载,不阻塞DOM树解析,但会阻塞DOM树渲染,且阻塞后续JS执行- JS加载,由于增删节点可能影响DOM解析,可以给script添加一个defer或者async的标签 - defer:不会阻塞DOM解析,等DOM解析完之后在运行,在DOMContentloaed之前- async: 不会阻塞DOM解析,等该资源下载完成之后立刻运行- DOM树渲染和Render树渲染(浏览器渲染过程) - 解析html并构建Dom树- 解析css并形成css树- 将cssom和dom合并成render树- 布局 render 树(layout)- 绘制 render 树(painting)- 回流重绘

5、回流/重绘

(1)定义

  • 重绘:即重新绘画,给元素更换颜色、背景等,改变页面样式,会重新渲染页面
  • 回流:增删dom节点、元素修改宽高时,改变页面布局,会再次构造dom树重新渲染页面

(2)特点

  • 回流必将引起重绘,重绘不一定引起回流

(3)优化

  • 多个属性尽量使用简写,例如:boder可以代替boder-width、boder-color、boder-style
  • 创建多个dom节点时,使用documentfragment创建
  • 避免使用table布局
  • 避免设置多层内联样式,避免节点层级过多
  • 避免使用css表达式
  • 将频繁重绘或回流的节点设置为图层,图层能够阻止该节点的渲染行为影响到别的节点(例:will-change\video\iframe等标签),浏览器会自动将该节点变为图层

6、https 与 http 区别

区别HTTPHTTPS端口80443证书无需证书需要证书(用于验证服务器身份)连接TCP 三次握手建立连接之后传输数据TCP 连接之后客户端与服务器进行 SSL 加密,确定对话密钥完成加密后传输数据协议超文本传输协议,信息明文传输ssl加密传输协议,为浏览器和服务器之间的通信加密,确保数据传输的安全安全性较低较高

7、跨域

(1)背景

  • 原因:域名、协议、端口号只要有一个不一致就会引起跨域,跨域是浏览器的安全机制导致的,仅存在浏览器中
  • 定义:跨域就是通过某些手段来绕过同源策略限制,实现不同服务器之间通信的效果

(2)方法

  • 前端解决不了,服务器端解决
  • 开发时可以通过配置代理服务器或者浏览器安装插件的方式临时解决,但上线后还是需要服务器做配置
  • 通过 jsonp 跨域 - 利用script标签的src属性实现跨域,通过将前端方法作为参数传递到服务器端,然后由服务器端注入参数后再返回,实现服务器端向客户端通信。由于使用script标签的src属性,JSONP 使用简单且兼容性不错,但仅限于 get 请求
  • postMessage 跨域
  • 跨域资源共享(CORS),需要浏览器和后端同时支持
  • nginx 代理跨域
  • nodejs 中间件代理跨域
  • WebSocket 协议跨域

8、五层协议的体系结构

  • 应用层:通过应用进程间的交互来完成特定网络应用
  • 运输层:负责向两台主机中进程之间的通信提供通用的数据传输服务TCP提供面向连接的、可靠的数据传输服务,传输单位为报文段UDP提供无连接的尽最大努力的数据传输服务,传输单位为用户数据报
  • 网络层:提供主机间的通信服务。路由器生成转发表,依据转发表转发分组至下一个路由器
  • 数据链路层:直连网络中相邻节点的链路上传输帧
  • 物理层:实现比特传输在这里插入图片描述

9、meta 标签

  • 为浏览器提供 html 的元信息(信息的信息)
<!-- 规定 html 字符编码 --><metacharset="UTF-8"><!-- 设置移动端的视区窗口 --><metaid="viewport"name="viewport"content="width=device-width; initial-scale=1.0; maximum-scale=1; user-scalable=no;"><!-- 移动端点击300ms 延时,可以对放大禁用 --><metaname="viewport"content="user-scalable=no"><metaname="viewport"content="initial-scale=1,maximum-scale=1"><!-- 设置http头 --><metahttp-equiv="content-Type"content="text/html; charset=gb2312"><!-- 图片403 --><metaname="referrer"content="no-referrer"/><!-- DNS 预解析 --><metahttp-equiv="x-dns-prefetch-control"content="on"><linkrel="dns-prefetch"href="//www.zhix.net">

10、登录实现

  • 用户第一次登录时,后端生成该用户对应token(唯一且有时效性)存入数据库并返回前端
  • 前端收到token后存储在localStorage,记录用户登录状态,下次发送用户相关请求时需携带token并放在header中
  • 后端需要设置Access-control-allow-headers : token避免跨域问题,后端给每个用户相关的接口都加上token校验
  • 每次用户切换界面时都进行路由守卫的拦截验证,登录状态为true,可以访问;false,不允许访问
  • 用户退出登录时删掉对应token

11、浏览器的多进程

(1)原因

  • 避免一个 tab页出错而导致整个浏览器崩溃
  • chrome 不同标签之间是进程,其他浏览器是线程

(2)组成

  • Browser 主进程(仅一个) - 负责页面交互、进程之间协调
  • GPU 加速进程
  • 渲染进程 - 内部多线程 - GUI 渲染线程 - 用来渲染的,构建 DOM 树、render 树,回流重绘等- 与 JS 引擎线程互斥- JS 引擎线程- 事件触发线程- 定时触发器线程- 异步 http 请求线程- 每个页面的渲染进程互不影响
  • 第三方插件进程

(3)进程和线程

区别线程进程规模小大关系组成进程包含线程资源调度和分配资源的基本单位拥有资源的基本单位并发执行同一进程不同线程不同进程间

12、进程间的通信方式

  • 无名管道通信:半双工通信,只能单向传输,一般用于父子通讯和兄弟通讯
  • 有名管道通信:半双工通信,只能单向传输,可以是无关进程之间通信
  • 消息队列
  • 信号量
  • 共享内存

四、Vue

1、MVVM 响应式

  • vue 采用数据劫持配合发布者-订阅者模式的方式,通过Object.defineProperty()来劫持各个属性的getter和setter,在数据变动时,发布消息给依赖收集器(dep中的subs),去通知(notify)观察者,做出对应的回调函数,更新视图
  • MVVM 作为绑定的入口,整合Observer,Compile和Watcher三者,通过Observer来监听model数据变化,通过Compile来解析编译模板指令,最终利用Watcher搭起Observer,Compile之间的通信桥路,达到数据变化引起视图更新;视图交互变化引起数据变更的双向绑定效果
  • M:Model,数据模型(保存数据,处理数据业务逻辑)
  • V:View,视图(展示数据,与用户交互)
  • VM:View Model,数据模型和视图的桥梁
  • MVVM设计模式最大的特点是支持数据的双向传递

2、nextTick

  • 定义:在下次 DOM 更新循环结束之后执行延迟回调。在修改数据之后立即使用这个方法,获取更新后的 DOM
  • 应用 - 在Vue生命周期函数created()中操作DOM,可以使用Vue.nextTick()回调函数- 在数据改变后要执行的操作,而这个操作需要等数据改变后而改变DOM结构的时候才进行操作,可以使用nextTick

3、生命周期函数

生命周期含义beforeCreate创建之前,此时还没有data和Method

Created

创建完成,此时data和Method可以使用了;
在Created之后beforeMount之前如果没有el选项的话那么此时生命周期结束,停止编译,如果有则继续beforeMount渲染之前

mounted

渲染完成,且vm实例中已添加$el;
已替换DOM元素(双括号中的变量),此时可以操作DOM(但无法获取元素高度等属性,可借助nextTick())beforeUpdatedata改变后,对应的组件重新渲染之前

updated

data改变后,对应的组件重新渲染完成beforeDestory实例销毁之前,此时实例仍可使用destoryed实例销毁后

4、computed 、watch、method的区别

  • computed:计算属性,其结果会被缓存,依赖的响应式属性变化才会重新计算
  • watch:一个对象,键是需要观察的表达式,值是对应回调函数,观察的数据改变后进行对应回调 - 深度监听,后面加一个deep:true- 监听完立马运行,后面加一个immediate:true
  • methods:一个具体操作方法,主要书写业务逻辑

5、Vue-router 模式

  • hash:监听hashchange事件实现前端路由,利用url中的hash模拟hash,保证url改变时,页面不会重新加载。
  • history:利用pushstate和replacestate将url替换但不刷新,一旦刷新就可能404,因为没有当前真正路径;解决这一问题需要后端配合,将不存在的路径重定向到入口文件

五、Git

1、常用命令

在这里插入图片描述

2、rebase 和 merge

  • 相同:都是合并分支
  • 不同: - rebase 不会产生额外的 commit- merge 会把这两个分支的遗漏 commit 记录重新创建一个commit保存起来


  • 选择:Merge具有更高的可追溯性,而Rebase则更整洁且易于审核,参考团队要求使用

六、微信小程序和uniapp

1、页面标签

  • 页面标签基本相同,如 view,text、scroll-view,input、picker、swiper 等

2、生命周期

  • 生命周期相同:onLoad,onShow,onPullDownRefresh、onReachBotton、onShareAppMessage 等

3、api

  • api 基本相同,wx 换成 uni
    类型apiwxwx.request、wx.showModal、wx.showToast、wx.showLoading、
    wx.chooseImage、wx.switchTab、wx.navigateo、wx.setStorageSync 等uniuni.request,uni.showModal、uni.showToast、uni.showLoading、
    uni.chooseImage、uni.switchTab、uni…navigateo、uni.setStorageSync 等

    4、事件

    类型触摸事件名称函数传参函数接收参数wxbindtap
    <view bindtap="click" data-id="id"></view>
    
    fn(e){ this.setData({ currentId:e.currentTarget.dataset.id }) }uni@click
    <view @click="click(id)"></view>
    
    fn(id){ this.currentId = id }

    5、for/if/src

    类型for循环if判断src动态接收图片wx
    <view wx:for="{{currentList}}" wx:for-index="s_index" wx:for-item="s_item"></view>
    
<view wx:if="{{isShow}}"></view>
<image src="{{item.img}}"></image>

uni

<view v-for="(s_item,s_index) in currentList"></view>
<view v-if="isShow"></view>
<image :src="item.img"></image>

6、页面传参

类型代码接收参数wx

<navigator url="/pages/live?id={{item.room_id}}"></navigator>

onLoad(options){}uni

<navigator :url="'/pages/live?id=' + item.room_id"></navigator>

onLoad(options){}

7、全局数据

类型定义调用wxglobalData:{baseUrl:“www.com”}getApp().globalData.baseUrlunithis.prototype.baseUrl = “https://www.ccc”this.baseUrl

8、数组拼接

类型代码wxthis.setData({ list:this.data.list.concat(res.list) })unithis.list = […this.list,…res.list]

9、阻止冒泡

类型代码wx

<view catchtap="clickTab">我是按钮</view>

uni

<view @click.stop="clickTab">我是按钮</view>

参考:
《想进互联网大公司?那这些题你总得会吧?前端面试题2022及答案前端面试题2022及答案》
《前端面试八股文(详细版)—上》
《微信小程序与uni-app的区别》


本文转载自: https://blog.csdn.net/weixin_64210950/article/details/130518950
版权归原作者 奔跑の大可爱 所有, 如有侵权,请联系我们删除。

“【面试】前端面试八股文”的评论:

还没有评论