js获取变量类型的方法有哪些,分别使用什么情况?

11种,Number,

String,

Boolean,

Object,

Array,

Json,

Function,

undefined,

Null,

Date,

RegExp,

Error

1、使用typeof能判断出四种,分别是number,string,boolean,object,剩余的均被检测为object

2、使用instanceof,根据instanceof的定义:判断参照对象的prototype属性所指向的对象是否在被行测对象的原型链上,这种变量判断可以检测出9种,undefined和null被检测为object,因为js中没有这种全局类型

对于number,string,boolean这三种类型,

​ 只有通过构造函数定义比如:

​ let num =new Number(1);

let num = 1;(这样定义是检测不出来的)

3、使用constructor检测,constructor是原型对象的属性指向构造函数。这种方式解决了instanceof的弊端,可以检测出除了undefined和null的9种类型

js中的this在哪些情况下分别指向哪些对象?

一、全局作用域或者普通函数自执行中this指向全局对象window

二、事件函数内部的this指向事件源:注意在事件函数中如果包含普通函数,普通函数自执行后,内部this还是指向window

三、对象方法调用时,this指向调用的对象

箭头函数this指向外层函数的调用者(箭头函数没有this)

call()和apply()的区别和作用?ES5的.bind()呢?

call、apply、bind的作用是改变函数运行时this的指向

var obj = {
name: “李四”,
age: 99,
myfun: function (kill, death) {
console.log(“名称:” + this.name + " 年龄:" + this.age + " 杀人数:" + kill + " 死亡:" + death);
},
};
var otherObj = {
name: “yasuo”,
age: 4,
};

obj.myfun.call(otherObj, '0', '10'); //名称:yasuo 年龄:4  杀人数:0  死亡:10
obj.myfun.apply(otherObj, ['0', '10']); //名称:yasuo 年龄:4  杀人数:0  死亡:10
obj.myfun.bind(otherObj, '0', '10')(); //名称:yasuo 年龄:4  杀人数:0  死亡:10

第一个参数:

 call 、bind 、 apply 这三个函数的第一个参数都是 this 的指向对象

第二个参数:

 call 的参数是直接放进去的,第二第三第 n 个参数全都用逗号分隔,直接放到后面apply 的所有参数都必须放在一个数组里面传进去 bind 除了返回是函数以外,它 的参数和 call 一样当然,三者的参数不限定是 string 类型,允许是各种类型,包括函数 、 object 等

使用new操作符是,js内部具体执行了哪些步骤?

var obj = new A();中一共实现了三步操作:

  1. 创建一个空对象obj var obj= {}
  2. 将构造函数的prototype赋给对象的___proto___ obj.__proto__ = A.prototype
  3. 构造函数对象的this指针指向obj A.call(obj)

写一个函数,实现将’ABCD’转化成’A B C D’

写一个对象深拷贝函数

浅拷贝(遇到对象只拷贝地址,且影响原始数据)

Object.assign(newobj,obj) 把obj的值复制给newobj

深拷贝

$.extend用于将一个或多个对象内容合并到目标对象

$.extend([deep],target,object1,[,objectN])

var newObject=$.extend(true,{},oldObject)

deep为true,表示深度拷贝

target目标对象

object1第一个被合并对象

objectN第N个被合并对象

JSON.stringify()是目前前端开发过程中最常用的深拷贝方式,原理是把一个对象序列化成为一个JSON字符串,将对象的内容转换成字符串的形式再保存在磁盘上,再用JSON.parse()反序列化将JSON字符串变成一个新的对象

var obj1 = {a:1,b:[1,2,3]
}
var str = JSON.stringify(obj1)
var obj2 = JSON.parse(str)
console.log(obj2); //{a:1,b:[1,2,3]}
obj1.a=2
obj1.b.push(4);
console.log(obj1); //{a:2,b:[1,2,3,4]}
console.log(obj2); //{a:1,b:[1,2,3]}

这是最常规的方法,思想很简单:就是对对象进行迭代操作,对它的每个值进行递归深拷贝。

for…in法

// 迭代递归法:深拷贝对象与数组
function deepClone(obj) {if (!isObject(obj)) {throw new Error('obj 不是一个对象!')}let isArray = Array.isArray(obj)let cloneObj = isArray ? [] : {}for (let key in obj) {cloneObj[key] = isObject(obj[key]) ? deepClone(obj[key]) : obj[key]}return cloneObj
}

介绍一下css盒子模型

盒模型: 内容(content)、填充(内边距padding)、边界(外边距margin)、 边框(border)

有两种, IE 盒子模型、标准 W3C 盒子模型;IE的content部分包含了 border 、padding

css选择器有哪些,css3伪类有哪些?

1.标签选择器

2.ID选择器

3.类选择器

4.组选择器

语法:选择器1,选择器2,选择器N{},eg:#box1,.box2,p{}//为id为box1,class为box2和p的元素共同设置样式。

5、通配符选择器

语法:{},eg:{font-size:16px}//将整个页面字体大小设为16px。

6.后代选择器

语法:选择器1选择器2{},eg:p.aa{}//选中指定祖先元素p的指定后代.aa。

7.子元素选择器

语法:父元素>子元素{},eg:p>.box{}//选中父元素p的指定子元素.box。注意与后代元素选择器的区别

8.伪类选择器

CSS3新增的伪类选择器:

:checked 被选中 主要用在input表单元素上

:not 排除

:last-child 最后一个元素

:nth-child(n) n表示具体的第几个 odd/2n+1 奇数 even/2n 偶数

:only-child 仅仅/唯一的元素

:nth-last-child(n) 倒数第几个元素 :nth-last-child(1) <=> :last-child

:first-of-type 第一个同级兄弟元素

:last-of-type 最后一个同级兄弟元素

:only-of-type 只有一个同级兄弟元素

:nth-of-type(n) 第几个同级兄弟元素

:nth-last-of-type(n) 倒数第几个同级兄弟元素

:empty 空内容

多终端页面适配怎么实现

百分比方案:使用 百分比% 定义 宽度自适应,高度 用**px**固定,根据可视区域实时尺寸进行调整,尽可能适应各种分辨率,通常使用max-width/min-width控制尺寸范围过大或者过小。

rem方案:em是相对长度单位,rem方案中的样式设计为相对于根元素font-size计算值的倍数。根据 屏幕宽度 设置html标签的font-size,在布局时使用 rem 单位布局,达到自适应的目的,是 弹性布局 的一种实现方式。

你了解并应用过的meta标签,及其作用

1.设置当前html文件的字符编码

2设置浏览器的兼容模式(让IE使用最新的浏览器渲染)

3.视口(快捷键:meta:vp)

作用:在移动浏览器中,当页面宽度超出设备,浏览器内部虚拟的一个页面容器,将页面容器缩放到设备那么大展示;
视口的宽度可以通过meta标签设置;
此属性为移动端页面视口设置;
width:视口的宽度,width=device-width:宽度是设备的宽度
initial-scale:初始化缩放,- initial-scale=1.0:不缩放
user-scalable:是否允许用户自行缩放,取值0或1,yes或no
minimum-scale:最小缩放
maximum-scale:最大缩放
一般设置了不允许缩放,就没必要设置最大最小缩放了。

常见的兼容问题?

谷歌默认字体大小

chrome下会让小于12px的文本字体默认为12px显示

box{ font-size: 12px; -webkit-transform: scale(0.75);}

图片默认有间距

解决方案:使用float属性为img布局
备注:因为img标签是行内属性标签,所以只要不超出容器宽度,img标签都会排在一行里,但是部分浏览器的img标签之间会有个间距。去掉这个间距使用float是正道

透明属性
用来设定元素透明度的opacity是CSS 3里的一个属性,现代浏览器都已经支持,对于老版本浏览器可以通过加入私有前缀来支持,对于IE6-IE8可以通过filter属性来支持,IE4-IE9都可以通过滤镜写法提供兼容支持。

opacity: 0.5;
-moz-opacity:0.5;
filter: alpha(opacity = 50); //IE6-IE8
filter: progid:DXImageTransform.Microsoft.Alpha(style = 0, opacity = 50); //IE4-IE9
媒体查询
对于IE9以下浏览器不支持CSS3媒体查询的问题,通常使用respond.js来作为兼容性解决方案。

阻止默认行为
W3C推荐的阻止默认行为的方式是event.preventDefault(),此方法只会阻止默认行为而不会阻止事件的传播。IE9之前的浏览器阻止默认行为需要使用window.event.returnValue = false。直接在事件处理函数中return false也能阻止默认行为,只在DOM0级模型中有效。此外,在jQuery中使用return false会同时阻止默认行为与事件传播,通常也会封装一个方法来实现默认行为的阻止。

handler.preventDefault = function(event) {
event = event || window.event;
if (event.preventDefault) {
event.preventDefault();
} else {
event.returnValue = false;
}
}
阻止事件冒泡
W3C推荐的阻止冒泡的方法是event.stopPropagation(),IE9之前则是使用window.event.cancelBubble = true;,通常也会封装一个方法来实现阻止事件冒泡。

handler.stopPropagation = function(event) {
event = event || window.event;
if (event.stopPropagation) {
event.stopPropagation();
} else {
event.cancelBubble = false;
}
}

滚动高度
获取窗口的滚动高度scrollTop需要采用兼容性写法,即使声明浏览器对于文档的处理也会有所不同。

var scrollTop = document.documentElement.scrollTop || document.body.scrollTop;
日期时间
使用new Date()构造函数生成日期时间对象,对于new Date(“2020-06-29”)语法在一些早期的浏览器会输出invalid date,这主要是因为早期浏览器不支持表达日期的-,而/才是被广泛支持的,所以在处理早期浏览器的兼容性时需要将-替换为/。

new Date(“2020-06-29”.replace(/-/g, “/”));

浮动引起的问题?清除浮动的方法

浮动定义:加了浮动的元素盒子在脱离文档流之后,会漂浮在标准流之上;
并且不占位置,它在浮起来之后,原来的位置就会漏给标准流的盒子;
浮动只有左右浮动。

主要目的:就是为了让多个块级元素可以在同一行显示出来

清除浮动主要是为了解决父元素在不设定高度的情况下,子元素因为浮动而引起的父元素内部高度为0的问题

清除浮动方法:

(1)是通过在浮动元素末尾添加一个空的标签

缺点:添加了无意义的标签,使得结构化较差。

(2)给浮动元素的父级元素添加overflow属性

在添加overflow属性后,浮动元素又回到父级元素层,撑起父元素高度,达到清除浮动效果。
缺点:内容增多的时候容易造成不会自动换行而导致的内容隐藏的问题,无法显示要溢出的元素。

(3)使用after伪元素清除浮动

html部分:

给浮动元素的父元素box1添加clearfix类

  <div class="box1 clearfix">

css部分

.clearfix:after{
content:"."; /设置内容为. 尽量不要为空,否则旧版本的浏览器会有空隙/
display:block; /转化为块级元素/
height:0; /高度为0/
visibility:hidden; /隐藏盒子/
clear:both; /清除浮动/
}
.clearfix{ /ie6.7浏览器的处理方式/
zoom:1;
/
是ie6.7能够识别的特殊符号,带有属性,只有ie6.7才执行
zoom是ie6.7的清除浮动的方法 */
}

(4)使用before和after双伪元素清除浮动(强烈推荐)
html部分:
给浮动元素的父元素box1添加clearfix类

css部分:

.clearfix:before,.clearfix:after{
content:"";
display:table;
}
.clearfix:after{
clear:both; /清除浮动/
}

如何对项目中资源进行优化,说出三种减少页面加载时间的方法

1.尽量减少页面中重复的HTTP请求数量

2.服务器启用gzip压缩功能:将要传输的文件压缩后传输到客户端再解压,在网络传输 数据量会大幅减小

3.压缩Javascript、CSS代码

4.优化图片文件,减小其尺寸

5.图像格式的选择(GIF:提供的颜色较少,可用在一些对颜色要求不高的地方)

6.css样式的定义放置在文件头部

7.Javascript脚本放在文件末尾

8.网址后面加上“/”:对服务器而言,不加斜杠服务器会多一次判断的过程,加斜杠就会直接返回网站设置的存放在网站根目录下的默认页面。

9.标明高度和宽度当浏览器知道了高度和宽度参数后,即使图片暂时无法显示,页面上也会腾出图片的空位,然后继续加载后面的内容。从而加载时间快了

如何解决跨域问题

跨域,指的是浏览器不能执行其他网站的脚本。它是由浏览器的同源策略造成的,是浏览器对JavaScript施加的安全限制。

同源策略指的是:协议+域名+端口三者皆相同,可以视为在同一个域,否则为不同域。同源策略限制了从同一个源加载的文档或脚本如何与来自另一个源的资源进行交互。

作用是一个用于隔离潜在恶意文件的重要安全机制

解决:

  • **jsonp**:只支持 GET,不支持 POST 请求,不安全 XSS
  • cors:需要后台配合进行相关的设置(跨域资源共享)
  • postMessage:配合使用 iframe,需要兼容 IE6、7、8、9
  • document.domain:仅限于同一域名下的子域
  • websocket:需要后台配合修改协议,不兼容,需要使用 http://socket.io
  • **proxy**:使用代理去避开跨域请求,需要修改 nginx、apache 等的配置
`JSONP` 请求本质上是利用了 “Ajax 请求会受到同源策略限制,而 script 标签请求不会” 这一点来绕过同源策略。客户端发送 script 请求,参数中带着处理返回数据的回调函数的名字 (通常是 callback),如请求 script 的 url 是:
http://127.0.0.1:8000/?callback=getMsg
服务端收到请求,以回调函数名和返回数据组成立即执行函数的字符串,比如:其中 callback 的值是客户端发来的回调函数的名字,假设回调函数的名字是 getMsg,返回脚本的内容就是:getMsg("{name: 'Yang Min', age: '8'}");
客户端收到 JavaScript 脚本内容后,立即执行脚本,这样就实现了获取跨域服务器数据的目的。

Nginx Proxy

Nginx 是一种高性能的反向代理服务器,可以用来轻松解决跨域问题。

反向代理拿到客户端的请求,将请求转发给其他的服务器,主要的场景是维持服务器集群的负载均衡,换句话说,反向代理帮其它的服务器拿到请求,然后选择一个合适的服务器,将请求转交给它。

js几种继承方式,ES5,ES6继承区别

1.原型链继承

2.构造函数继承

  1. 组合继承
  2. 原型式继承
  3. 寄生式继承
  4. 寄生组合式继承

在ES5中,比较好的继承方式时,通过构造函数继承,继承属性;再通过原型链继承,继承方法;
而ES6中,直接通过extends关键字进行继承。

它们主要的区别在于:
ES5中,先创建子类的实例this,再通过父类构造函数或原型向其上添加属性或方法;而ES6中,是先通过super创建父类实例this,再向其中添加属性或方法。
ES6中,有两条原型链。

class A extends B{}A.__proto__ === B;  //继承属性A.prototype.__proto__ == B.prototype;//继承方法

如何理解闭包,哪些操作造成内存泄露

**闭包:**能够访问其他函数内部变量的函数

闭包的作用
1.访问其他函数内部变量
2.保护变量不被内存回收机制回收
3.避免全局变量被污染 方便调用上下文的局部变量 加强封装性

闭包的缺点
闭包长期占用内存,内存消耗很大,可能导致内存泄露

如何避免闭包引起的内存泄漏
1,在退出函数之前,将不使用的局部变量全部删除。可以使变量赋值为null;

2,避免变量的循环赋值和引用。

造成内存泄露的操作

  1. setTimeout 的第一个参数使用字符串而非函数的话,会引发内存泄漏。

  2. 闭包

  3. 控制台日志

  4. 循环引用(在两个对象彼此引用且彼此保留时,就会产生一个循环)

    一个DOM对象被一个Javascript对象引用,与此同时又引用同一个或其它的Javascript对象,这个DOM对象可能会引发内存泄漏。`

    这个DOM对象的引用将不会在脚本停止的时候被垃圾回收器回收。要想破坏循环引用,引用DOM元素的对象或DOM对象的引用需要被赋值为null。

    5.DOM插入顺序

    当2个不同范围的 DOM 对象连添加到一起的时候一个临时的对象会被创建。这个DOM对象改变范围到document时,那个临时对象就没用了。也就是说, DOM 对象应该按照从当前页面存在的最上面的 DOM 元素开始往下直到剩下的 DOM 元素的顺序添加,这样它们就总是有同样的范围,不会产生临时对象。
    

js中作用域与变量提升

  1. 作用域(scope):作用域就是变量绑定(name binding)的有效范围。就是说在这个作用域中,这个变量绑定是有效的,出了这个作用域变量绑定就无效了。

  2. JS使用的是静态作用域,即一个函数使用的变量如果没在自己里面,会去定义的地方查找,而不是去调用的地方查找。去调用的地方找到的是动态作用域。

  3. 用let和const申明的变量不会提升,var会提升
    `函数声明和变量声明都会被提升,但是函数会首先被提升,然后才是变量`
    

js中循环有哪些

1.while 循环:

2. do……while循环

3.for循环:

4.增强for…in循环:

注意:fo…in循环一般用于对象的遍历,但是这里有一个坑需要注意:

​ 任何对象都继承了Object对象,或者其它对象,继承的类的属性是默认不可遍历的,for... in循环遍历的时候会跳过,但是这个属性是可以更改为可以遍历的,那么就会造成遍历到不属于自身的属性。

如果继承的属性是可遍历的,那么就会被for...in循环遍历到。但如果只想遍历自身的属性,使用for...in的时候,应该结合使用hasOwnProperty方法,在循环内部判断一下,某个属性是否为对象自身的属性。否则就可以产生遍历失真的情况。

5.map()循环:

​ map方法将数组的所有成员依次传入参数函数,然后把每一次的执行结果组成一个新数组返回。

​ 注意:是返回一个新数组,而不会改变原数组。

map方法接受一个函数作为参数。该函数调用时,map方法向它传入三个参数:当前成员、当前位置和数组本身。

[1, 2, 3].map(function(elem, index, arr) {

​ return elem * index;

});

// [0, 2, 6]

map()循环还可以接受第二个参数,用来绑定回调函数内部的this变量,将回调函数内部的this对象,指向第二个参数,间接操作这个参数(一般是数组)。

var arr = [‘a’, ‘b’, ‘c’];

[1, 2].map(function (e) {

​ return this[e];

}, arr)

// [‘b’, ‘c’]

6.forEach循环

7.filter()过滤循环

8.some(),every()循环遍历,统计数组是否满足某个条件

这两个方法类似“断言”(assert),返回一个布尔值,表示判断数组成员是否符合某种条件。

**9.reduce(),reduceRight()**方法可依次处理数组的每个成员

reduce方法和reduceRight方法依次处理数组的每个成员,最终累计为一个值。它们的差别是,reduce是从左到右处理(从第一个成员到最后一个成员),reduceRight则是从右到左(从最后一个成员到第一个成员),其他完全一样。

10.Object.keys遍历对象的属性**

11.Object.getOwnPropertyNames()遍历对象的属性**

Object.getOwnPropertyNames方法与Object.keys类似,也是接受一个对象作为参数,返回一个数组,包含了该对象自身的所有属性名。但它能返回不可枚举的属性。

使用JQuery 的遍历:

1. $.grep()筛选遍历数组**

2.$.each()筛选遍历数组或json对象

3.$.inArray()筛选遍历数组

4.$.map()筛选遍历数组

MVC和MVVM的差别

JS原生数据双向绑定

数据层改变视图层 Objcect.defineProperty() 监听数据改变-set里影响视图

视图层改变数据层 视图层绑定事件 ,把值赋给变量 对象.属性名=e.target.value

vue2- Objcect.defineProperty 无法深层监听 新属性要用set添加

vue3-Proxy(代理)

MVC是比较直观的架构模式,用户操作->View(负责接收用户的输入操作)->Controller(业务逻辑处理)->Model(数据持久化)->View(将结果反馈给View)MVC是单向通信

MVVM是将“数据模型数据双向绑定”的思想作为核心,因此在View和Model之间没有联系,通过ViewModel进行交互,而且Model和ViewModel之间的交互是双向的,因此视图的数据的变化会同时修改数据源,而数据源数据的变化也会立即反应到View上。

MVVM主要解决了MVC中大量的DOM操作使页面渲染性能降低,加载速度变慢,影响用户体验。

分别用css2和css3实现块级元素在父元素内水平和垂直居中

如何阻止事件冒泡

1.event.stopPropagation();
事件处理过程中,阻止了事件冒泡,但不会阻击默认行为(执行超链接的跳转)
2.returnfalse;
事件处理过程中,阻止了事件冒泡,也阻止了默认行为(不执行超链接的跳转)
还有一种与冒泡有关的:
3.event.preventDefault();
事件处理过程中,不阻击事件冒泡,但阻击默认行为(它只执行所有弹框,却没有执行超链接跳转)

瀑布流实现基本原理

瀑布流,又称瀑布流式布局。

实现原理:

对容器中已有数据块元素进行第一次计算1 容器总宽度 2 列宽度 3 最小列数 ,得到列数后,用一个数组存放盒子所有高度,找出最小高度。之后根据序列号更新高度;

对于滚动加载:即滚动到哪个高度后,需要去加载数据,其实这个就是列的最小高度值,这样当前滚动值和最小高度值比较一下即可判断出来,是否要触发加载数据;就是写一个函数,用来判断是否达到加载图片条件,如果达到,就开始加载。比如获得最后一张图片的offsetTop,可视区高度,滚动距离,也就是当图片的offsetTop小于可视区高度和滚动距离之和的情况下,此时就应该加载了,不过条件可以随便定,也可以等滚动到图片的一半时候在触发加载条件,

Lazyload实现基本原理

核心原理是:

1 设置一个定时器,计算每张图片是否会随着滚动条的滚动,而出现在视口(也就是浏览器中的 展现网站的空白部分 )中;

2 为标签设置一个暂存图片URL的自定义属性(例如loadpic),当图片出现在视口时,再将loadpic的值赋给图片的src属性;

列举原生查找DOM的方法

JS获取DOM元素的方法(8种)

  • 通过ID获取(getElementById)
  • 通过name属性(getElementsByName)
  • 通过标签名(getElementsByTagName)
  • 通过类名(getElementsByClassName)
  • 通过选择器获取一个元素(querySelector)
  • 通过选择器获取一组元素(querySelectorAll)
  • 获取html的方法(document.documentElement)
    document.documentElement是专门获取html这个标签的
  • 获取body的方法(document.body)
    document.body是专门获取body这个标签的。

ES6数组新特性

map:原来数组有多少个,map 处理之后还是那么多个。参数:item,index,array

filter: 过滤掉不符合条件的。参数:item,index,array

forEach: 遍历。仅仅只是循环用,无返回值,也不会改变原数组。 参数:item,index,array

Array.from(arr)

Array.from(arr)的作用就是将 array-like 类型的数据转变成 array。

分别写出ES5中新增的存储本地数据的方法,并说明区别

javaScript有三种数据存储方式,分别是:

sessionStorage

localStorage

cookier

相同点:都保存在浏览器端

不同点:

①传递方式不同

cookie数据始终在同源的http请求中携带(即使不需要),即cookie在浏览器和服务器间来回传递。

sessionStorage和localStorage不会自动把数据发给服务器,仅在本地保存。

②数据大小不同

cookie数据还有路径(path)的概念,可以限制cookie只属于某个路径下。
存储大小限制也不同,cookie数据不能超过4k,同时因为每次http请求都会携带cookie,所以cookie只适合保存很小的数据,如会话标识。

sessionStorage和localStorage 虽然也有存储大小的限制,但比cookie大得多,可以达到5M或更大。

③数据有效期不同

sessionStorage:仅在当前浏览器窗口关闭前有效,自然也就不可能持久保持;

localStorage:始终有效,窗口或浏览器关闭也一直保存,因此用作持久数据;

cookie只在设置的cookie过期时间之前一直有效,即使窗口或浏览器关闭。

④作用域不同

sessionStorage不在不同的浏览器窗口中共享,即使是同一个页面;

localStorage 在所有同源窗口中都是共享的;

cookie也是在所有同源窗口中都是共享的。

Web Storage 支持事件通知机制,可以将数据更新的通知发送给监听者。
Web Storage 的 api 接口使用更方便。

介绍下Generator函数,以及如何使用

ArrayBuffer和Array有什么区别

1、数组里面可以放数字、字符串、布尔值以及对象和数组等,ArrayBuffer放0和1组成的二进制数据
2、数组放在堆中,ArrayBuffer则把数据放在栈中(所以取数据时后者快)
3、ArrayBuffer初始化后固定大小,数组则可以自由增减。

axios与jQuary的ajax有什么区别

区别:

axios是通过Promise实现对ajax技术的一种封装,就像jquery对ajax的封装一样,简单来说就是ajax技术实现了局部数据的刷新,axios实现了对ajax的封装,axios有的ajax都有,ajax有的axios不一定有,总结一句话就是axios是ajax,ajax不止axios

优缺点:

ajax:

1、本身是针对MVC编程,不符合前端MVVM的浪潮

2、基于原生XHR开发,XHR本身的架构不清晰,已经有了fetch的替代方案,jquery整个项目太大,单纯使用ajax却要引入整个jquery非常不合理(采取个性化打包方案又不能享受cdn服务)

3、ajax不支持浏览器的back按钮

4、安全问题ajax暴露了与服务器交互的细节

5、对搜索引擎的支持比较弱

6、破坏程序的异常机制

7、不容易调试
8、局部刷新

axios:

1、从node.js创建http请求

2、支持Promise API

3、客户端防止CSRF(网站恶意利用)

4、提供了一些并发请求的接口

vue-router有哪几种导航钩子

有三种方式可以植入路由导航过程中:

  1. 全局的
  2. 单个路由独享的
  3. 组件级的
  4. 全局导航钩子:

全局导航钩子主要有两种钩子:前置守卫、后置钩子,

注册一个全局前置守卫:

const router = new VueRouter({ … });
router.beforeEach((to, from, next) => {
// do someting
});

这三个参数 to 、from 、next 分别的作用:

to: Route,代表要进入的目标,它是一个路由对象

from: Route,代表当前正要离开的路由,同样也是一个路由对象

next: Function,这是一个必须需要调用的方法,而具体的执行效果则依赖 next 方法调用的参数

next():进入管道中的下一个钩子,如果全部的钩子执行完了,则导航的状态就是 confirmed(确认的)
next(false):这代表中断掉当前的导航,即 to 代表的路由对象不会进入,被中断,此时该表 URL 地址会被重置到 from 路由对应的地址
next(‘/’) 和 next({path: ‘/’}):在中断掉当前导航的同时,跳转到一个不同的地址
next(error):如果传入参数是一个 Error 实例,那么导航被终止的同时会将错误传递给 router.onError() 注册过的回调
注意:next 方法必须要调用,否则钩子函数无法 resolved

对于全局后置钩子:

router.afterEach((to, from) => {
// do someting
});

不同于前置守卫,后置钩子并没有 next 函数,也不会改变导航本身

  1. 路由独享的钩子

顾名思义,即单个路由独享的导航钩子,它是在路由配置上直接进行定义的:

cont router = new VueRouter({
routes: [
{
path: ‘/file’,
component: File,
beforeEnter: (to, from ,next) => {
// do someting
}
}
]
});

至于他的参数的使用,和全局前置守卫是一样的

  1. 组建内的导航钩子

组件内的导航钩子主要有这三种:beforeRouteEnter、beforeRouteUpdate、beforeRouteLeave。他们是直接在路由组件内部直接进行定义的

我们看一下他的具体用法:

const File = {
template: <div>This is file</div>,
beforeRouteEnter(to, from, next) {
// do someting
// 在渲染该组件的对应路由被 confirm 前调用
},
beforeRouteUpdate(to, from, next) {
// do someting
// 在当前路由改变,但是依然渲染该组件是调用
},
beforeRouteLeave(to, from ,next) {
// do someting
// 导航离开该组件的对应路由时被调用
}
}
需要注意是:

beforeRouteEnter 不能获取组件实例 this,因为当守卫执行前,组件实例被没有被创建出来,剩下两个钩子则可以正常获取组件实例 this

但是并不意味着在 beforeRouteEnter 中无法访问组件实例,我们可以通过给 next 传入一个回调来访问组件实例。在导航被确认是,会执行这个回调,这时就可以访问组件实例了,如:

beforeRouteEnter(to, from, next) {
next (vm => {
// 这里通过 vm 来访问组件实例解决了没有 this 的问题
})
}
注意,仅仅是 beforRouteEnter 支持给 next 传递回调,其他两个并不支持。因为归根结底,支持回调是为了解决 this 问题,而其他两个钩子的 this 可以正确访问到组件实例,所有没有必要使用回调

最后是完整的导航解析流程:

导航被触发
在失活的组件里调用离开守卫
调用全局的 beforeEach 守卫
在重用的组件里调用 beforeRouteUpdate 守卫
在路由配置里调用 beforEnter
解析异步路由组件
在被激活的组件里调用 beforeRouteEnter
调用全局的 beforeResolve 守卫
导航被确认
调用全局的 afterEach 钩子
触发 DOM 更新
在创建好的实例调用 beforeRouteEnter 守卫中传给 next 的回调函数

v-model是什么,怎么使用

v-model用于表单数据的双向绑定,其实它就是一个语法糖,这个背后就做了两个操作:

v-bind绑定一个value属性
v-on指令给当前元素绑定input事件

v-model.trim去除首尾空格

vue中的标签怎么绑定事件

1、 直接在标签中写js方法

 <button v-on:click="alert('hi')">执行方法的第一种写法</button>

2、调用method的办法

 <button v-on:click="run()">执行方法的第一种写法</button>

(1)方法传参,方法直接在调用时在方法内传入参数

 <button @click="deleteData('111')">执行方法传值111</button>

(2)传入事件对象

 <button data-aid='123' @click="eventFn($event)">事件对象</button>

3.事件修饰符

@click.stop='show()'    只要在事件后面加 .stop  就可以阻止事件冒泡
@click.prevent='show()'   只要在事件后面加 .prevent  就可以阻止默认事件。

capture // 添加事件监听器时使用事件捕获模式,即在捕获模式下触发

实例:在点击最里层的点击6时,gett方法先执行,因为gett方法在捕获模式执行的,先与冒泡事件。下列执行顺序 geet->set->tz ,因为后俩个还是冒泡模式下触发的事件。

<div v-on:click.capture="gett">外部点击5<div  v-on:click="tz">内部点击5<div  v-on:click="set">点击6</div></div>
</div>

capture // 添加事件监听器时使用事件捕获模式,即在捕获模式下触发

实例:在点击最里层的点击6时,gett方法先执行,因为gett方法在捕获模式执行的,先与冒泡事件。下列执行顺序 geet->set->tz ,因为后俩个还是冒泡模式下触发的事件。

<div v-on:click.capture="gett">外部点击5<div  v-on:click="tz">内部点击5<div  v-on:click="set">点击6</div></div>
</div>

once //只触发一次

<div  v-on:click.once="tz">once</div>

、键盘事件

方法一:@keydown=‘show()’ 当然我们传个$event 也可以在函数中获 ev.keyCode

if(ev.keyCode==13){alert('你按了回车键!')
}

方法二:

  <input type="text" @keyup.enter="show()">回车执行

简述vue生命周期

1.创建部分(create),就是vue实例被初始化,简单的说就是我们在代码中进行了这个操作 var app = new Vue() ,之后就进入的vue生命周期的创建阶段。在创建阶段中会有两个提供给我们可编程的接口,分别是beforeCreate 和 created。 这两个接口都是在创建阶段触发,但是两个接口又有所不同,beforeCreate比created要先触发,即vue实例初始化后,没有进行数据读取前就触发,如果在此时进行读取data中的数据就会提示unfined。 created 是在实例创建完成后再被调用,此时data中的数据已经写入完成,但是还没有进行dom的挂载,也就还没有与页面进行关联,下面进入挂载阶段。
2.挂载阶段(mount),该阶段就是将页面中dom挂载到实例化后的vue对象上。简单的说就是执行了 el: ‘#dom’。该阶段同样有两个接口供我们进行编程,分别是 beforemount 和 mounted 。这两个接口的主要区别在与以有没有将dom挂载到实例对象上,beforemount 是在挂载之前触发,仅对模板进行解析,如果此时输出需要挂载的dom的innerHTML的话,会将模板原样输出,并没有将数据进行渲染。 mounted 是在dom挂载之后,可以将data中的数据渲染的页面上。
3.更新阶段(update),该阶段是在页面上的数据在第一次加载之后再次进行更新的时候。同样对应两个接口 beforeupdate 和 update。这两个接口的差异主要在于有没有对页面dom进行渲染。在我们对data中的数据进行修改,且修改完成后触发 beforeupdate ,此时data中的属性值已经是修改完成的状态,但是没有对页面的dom进行渲染。update 就是将数据渲染到页面上。
4.更新阶段,在正常的使用中我们会多次的经常处于更新阶段,对页面的数据进行各种修改。但是为了满足将不必要的事件关闭,释放内存,就还需要销毁阶段。销毁阶段(destory),在一个实列被销毁后,该实例所绑定的所有事件都会失效,监听器也会被移除。该阶段对应两个接口 beforeDestroy 和 destroy。deforeDestory是在实例需要被销毁但是还没有销毁之前调用,此时该实例的的绑定的各类事件、监听器仍然可用。 destroy是在实例销毁后调用,此时该实例的所有东西都不能使用,但是页面上的数据仍保持页面最后一次渲染的数据。

父组件如何传值给子组件

父组件在调用子组件的地方,添加一个自定义的属性,属性的值就是需要传递给子组件的值,如果需要传递的值是一个变量,或者是boolean,或者是number类型,需要使用绑定属性

<my-list :list="list" :num="list.length"></my-list>

* 在子组件定义的地方,添加一个选项 props,方式一 props的值为数组,元素为自定义的属性名

const List = {props: ['list'],template: '#list'
}

keep-alive是什么,有什么作用

keep-alive这个组件的作用就是能够缓存不活动的组件,一般情况下,组件进行切换的时候,默认会进行销毁,如果有需求,某个组件切换后不进行销毁,而是保存之前的状态,那么就可以利用keep-alive来实现

属性

该标签有两个属性include与exclude:

  • include:字符串或者正则表达式。只有匹配的组件会被缓存
  • exclude:字符串或者正则表达式。任何匹配的组件都不会被缓存。
  • 生命钩子
    • keep-alive提供了两个生命钩子,分别是activated与deactivated。因为keep-alive会将组件保存在内存中,并不会销毁以及重新创建,所以不会重新调用组件的created、mounted这些函数。
    • 被 keep-alive 包裹的组件被缓存之后有两个独有的生命周期: activated 和 deactivated。activated 生命周期在组件激活时调用、deactivated 生命周期在组件停用时调用。

子组件如何传值给父组件

子组件通过**this.$emit()**的方式将值传递给父组件

1. 在子组件中需要向父组件传值处使用this.$emit(“function”,param); //其中function为父组件定义函数,param为需要传递参数

. 在父组件中子组件引用处添加函数v-on:function=“function1”; //其中function为子组件中定义函数,function1为父组件定义函数–用于接收子组件传值并进行相应数据处理,可定义为同一名称

简述Flux架构

vue数据双向绑定

vue数据双向绑定是通过数据劫持结合发布者-订阅者模式的方式来实现的

实现mvvm的双向绑定,就必须要实现以下几点:
1、实现一个数据监听器Observer,能够对数据对象的所有属性进行监听,如有变动可拿到最新值并通知订阅者
2、实现一个指令解析器Compile,对每个元素节点的指令进行扫描和解析,根据指令模板替换数据,以及绑定相应的更新函数
3、实现一个Watcher,作为连接Observer和Compile的桥梁,能够订阅并收到每个属性变动的通知,执行指令绑定的相应回调函数,从而更新视图
4、mvvm入口函数,整合以上三者

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Y8lYwghp-1622632598973)(C:\Users\Administrator\AppData\Roaming\Typora\typora-user-images\image-20210425143213612.png)]

vue是通过Object.defineProperty()来实现数据劫持,只实现了对属性的set/get监听

isNaN作用

isNaN() 函数可用于判断其参数是否是 NaN,用于检查其参数是否是非数字值。(比如被 0 除后得到的结果)。

如果把 NaN 与任何值(包括其自身)相比得到的结果均是 false,所以要判断某个值是否是 NaN,不能使用 == 或 === 运算符。正因为如此,isNaN() 函数是必需的。

什么是重构,回流,怎么避免回流

  1. 当render tree中的一部分(或全部)因为元素的规模尺寸,布局,隐藏等改变而需要重新构建。这就称为回流(reflow)。

  2. 当render tree中的一些元素需要更新属性,而这些属性只是影响元素的外观,风格,而不会影响布局的,比如background-color。则就叫称为重绘。

  3. 如何减少回流、重绘

    1. 直接改变className,如果动态改变样式,则使用cssText(考虑没有优化的浏览器)

    2. 让要操作的元素进行”离线处理”,处理完后一起更新

    3.不要经常访问会引起浏览器flush队列的属性,如果你确实要访问,利用缓存
    4.让元素脱离动画流,减少回流的Render树的规模(即让动画的元素脱离文档流,使用absolute定位等等)。

如何点击一个按钮使用jQuery隐藏一个图片

  1. 方法一

  2. 这里通过自定义一个 class : show 来判断 div 是显示或隐藏

  3. hasClass() 是否存在某个class

  4. hide() 隐藏对象

  5. show() 显示对象

  6. removeClass() 移除一个class

  7. addClass() 添加一个class

  8. 除此,还可以通过jquery设置这个 div 的 css : display:none/block 来实现隐藏/显示

$(document).ready()是个什么函数?为什么用它

$(document).ready()和传统的方法<body οnlοad=”load()”> 相似,不同的是onload()的方法是在页面加载完成后才发生,这包括DOM元素和其他页面元素(例如图片)的加载

而**$(document).ready()所要执行的代码是在DOM元素被加载完成的情况下执行**,所以,使用**document.ready()方法的执行速度比onload()的方法要快**

Javascript 只有在DOM元素已经定义以后才可以对其执行某种操作,jQuery使用document.ready来保证所要执行的代码是在DOM元素被加载完成的情况下执行。

jQuery中最快选择器是哪个?jQuery中最慢选择器是哪个?

ID > Tag > Class

  • ID 选择器是速度最快的,这主要是因为它使用 JavaScript 的内置函数 getElementById()
  • 其次是类型选择器,因为它使用 JavaScript 的内置函数 getElementsByTag()
  • 速度最慢的是 Class 选择器,其需要通过解析 HTML 文档树,并且需要在浏览器内核外递归,这种递归遍历是无法被优化的。

选择器性能优化建议

  • 尽量使用 ID 选择器
  • 少直接使用 Class 选择器,尽量结合 Tag 使用,如 input.myclass
  • 多用父子关系,少用嵌套关系
  • 缓存 jQuery 对象
  • 链式调用

什么是闭包

闭包就是能够读取其他函数内部变量的函数

闭包简单理解成"定义在一个函数内部的函数"

所以,在本质上,闭包就是将函数内部和函数外部连接起来的一座桥梁。

优点: 避免全局变量的污染,同时,局部变量没有被销毁,驻留在内存中,还可以被访问
缺点: 使用不当,会造成内存泄露

**解决方法:**在退出函数之前,将不使用的局部变量全部删除。

js怎么清空数组

1.splice函数

arrayObject.splice(index,howmany,element1,…,elementX)

index:必选,规定从何处添加/删除元素。

howmany:必选,规定应该删除多少元素。未规定此参数,则删除从 index 开始到原数组结尾的所有元素。

element1:可选,规定要添加到数组的新元素。

2.给数组的length赋值为0

该方法保留了数组其它属性。

赋予数组的长度小于本身的长度,数组中后面的元素将被截断。

赋予数组的长度大于本身的长度,将扩展数组长度,多的元素为undefined。

3.直接赋予新数组 []

这种方式为将arr重新赋值为空数组,之前的数组如果没有被引用,将等待垃圾回收。

cookie,sessionStorage,localeStorage的区别

共同点:都是保存在浏览器端、且同源的
区别:

一、存储大小

  1. cookie数据大小不能大于4K;
  2. localStorage和sessionStorage则可以达到5M;

二、有效时间

  1. cookie在设置的有效期内一直有效;
  2. localStorage存储持久数据,只要不手动清除则一直存在;
  3. sessionStorage数据在当前浏览器关闭后就会被自动清除

三、数据与服务器间的交互方式

  1. cookie的数据会自动传递到服务器端,服务器端也可以写cookie到客户端

  2. localStorage和sessionStorage不会把数据自动传到服务器端,仅在本地存储

    [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-dRdnKBMn-1622632598976)(C:\Users\Administrator\AppData\Roaming\Typora\typora-user-images\image-20210426103317878.png)]

vue中使用插件的步骤

import PageTools from ‘./PageTools’
import UploadExcel from ‘./UploadExcel’

// 以插件格式注册全局组件要先提供统一注册的入口文件,再去main注册插件

// 插件的初始化, 插件给你提供的全局的功能, 都可以在这里配置

const MyPlugin = {

install(Vue) { // 进行组件的全局注册

Vue.component(‘PageTools’, PageTools) // 注册工具栏组件

Vue.component(‘UploadExcel’, UploadExcel)// 注册导入excel组件

console.log(‘install被调用,传入的参数是’, Vue)

}

}

export default MyPlugin

//在main.js文件里, 以插件格式注册全局组件

import Components from ‘./components’

Vue.use(Components)

HTTP请求报文与响应报文格式

一个HTTP请求报文由请求行(request line)、请求头部(header)、空行和请求数据4个部分组成

.请求头

请求行由请求方法字段、URL字段和HTTP协议版本字段3个字段组成,它们用空格分隔。例如,GET /index.html HTTP/1.1。

HTTP协议的请求方法有GET、POST、HEAD、PUT、DELETE、OPTIONS、TRACE、CONNECT。

.空行

最后一个请求头之后是一个空行,发送回车符和换行符,通知服务器以下不再有请求头。

HTTP响应也由三个部分组成,分别是:状态行、消息报头、空行、响应正文。

HTTP请求GET和POST的区别

1.GET提交,请求的数据会附在URL之后(就是把数据放置在HTTP协议头<request-line>中)

POST提交:把提交的数据放置在是HTTP包的包体<request-body>中

GET提交的数据会在地址栏中显示出来,而POST提交,地址栏不会改变

2.传输数据的大小:

HTTP协议没有对传输的数据大小进行限制,HTTP协议规范也没有对URL长度进行限制,GET:特定浏览器和服务器对URL长度有限制

GET提交时,传输数据就会受到URL长度的限制

POST:由于不是通过URL传值,理论上数据不受限

3.安全性:

POST的安全性要比GET的安全性高。

GET提交数据,用户名和密码将明文出现在URL上,因为(1)登录页面有可能被浏览器缓存, (2)其他人查看浏览器的历史纪录,那么别人就可以拿到你的账号和密码了

浏览器中输入URL到整个页面响应期间经历了哪些过程

1.域名解析
2.发起tcp三次握手
3.发起tcp请求后发起http请求
4.服务器响应http请求,浏览器得到html代码
5.浏览器解析html代码,并请求html代码中的资源
6.浏览器对页面进行渲染呈现给客户

如何获取浏览器URL中的查询字符串的参数

什么是跨域?跨域请求资源方法有哪些

由于浏览器同源策略,凡是发送请求url的协议、域名、端口三者之间任意一个与当前页面地址不同即为跨域

jsonp
最常见的一种跨域方式,其背后原理就是利用了script标签不受同源策略的限制,在页面中动态插入了script,script标签的src属性就是后端api接口的地址,并且以get的方式将前端回调处理函数名称告诉后端,后端在响应请求时会将回调返还,并且将数据以参数的形式传递回去。

缺点:

1、这种方式无法发送post请求(这里)

2、另外要确定jsonp的请求是否失败并不容易,大多数框架的实现都是结合超时时间来判定。

porxy代理

定义和用法:proxy代理用于将请求发送给后台服务器,通过服务器来发送请求,然后将请求的结果传递给前端。

实现方法:Nginx反向代理

注意点:1、如果你代理的是https协议的请求,那么你的proxy首先需要信任该证书(尤其是自定义证书)或者忽略证书检查,否则你的请求无法成功。

**跨域资源共享(CORS)**后端方法

跨域解决方法

(1)document.domain + iframe跨域
(2)location.hash + iframe跨域
(3)window.name + iframe跨域
(4)postMessage跨域
(5)通过jsonp跨域
(6)跨域资源共享(CORS)
(7)Nginx反向代理
(8)nodejs中间件地代理跨域
(9)WebSocket协议跨域

一般来说,前三个是iframe的跨域;窗口之间JS跨域postMessage;简单的跨域请求jsonp即可,复杂的用cors;开发环境下接口跨域用nginx反向代理或node中间件比较方便。

js内存管理机制

内存管理,是 js 从创建变量到垃圾回收的一个过程

生命周期

  1. 分配你所需要的内存(变量声明的时候)
  2. 使用分配的内存(读,写)
  3. 不需要的时候回收(或者释放)内存

js 的内存空间

分三种:

  • 栈:存放变量,包括基础数据类型的变量及对象的指针
  • 堆:存放引用数据类型的值
  • 池:一般也归类为栈,保存常量

垃圾回收的原理

找出那些不再继续使用的变量,然后释放其占用的内存。

生命周期

  1. 分配你所需要的内存(变量声明的时候)

  2. 使用分配的内存(读,写)

  3. 不需要的时候回收(或者释放)内存

    js 的内存空间

    分三种:

    • 栈:存放变量,包括基础数据类型的变量及对象的指针

    • 堆:存放引用数据类型的值

    • 池:一般也归类为栈,保存常量

      垃圾回收的原理

      找出那些不再继续使用的变量,然后释放其占用的内存。

    浏览器的垃圾回收策略

    1.标记清除

    2.引用计数算法:简单说就是,有引用时 +1,没有引用 -1,引用计数为 0 时回收。那么就有了循环引用的对象不能被回收的情况,因为它的引用计数永远不能为 0,除非手动把引用置为 null

    内存泄漏

    不再用到的内存,没有及时释放,就叫做内存泄漏

    js 中哪些操作会引发内存泄漏:

    • 闭包
    • 用完的定时器没有清除
    • 死循环(例如没有结束条件的递归,循环引用的对象)
    • 意外的全局变量(例如没有使用 var, let, const 定义的变量)
    • 被移除的DOM节点上的绑定事件没有清除

js面向对象继承实现

1.原型链继承:new一个构造器函数创建出一个新对象,把老对象的东西都拿过来

2.构造继承:借用构造函数的基本思想就是利用call或者apply把父类中通过this指定的属性和方法复制(借用)到子类创建的实例中

**核心:**使用父类的构造函数来增强子类实例,等于是复制父类的实例属性给子类(没用到原型)

缺点: 方法都在构造函数中定义, 只能继承父类的实例属性和方法,不能继承原型属性/方法,无法实现函数复用

3、组合继承

组合继承(所有的实例都能拥有自己的属性,并且可以使用相同的方法,组合继承避免了原型链和借用构造函数的缺陷,结合了两个的优点,是最常用的继承方式)

**核心:**通过调用父类构造,继承父类的属性并保留传参的优点,然后再通过将父类实例作为子类原型,实现函数复用

**缺点:**调用了两次父类构造函数,生成了两份实例

4、寄生组合继承

**核心:**通过寄生方式,砍掉父类的实例属性,这样,在调用两次父类的构造的时候,就不会初始化两次实例方法/属性,避免的组合继承的缺点

**缺点:**堪称完美,但实现较为复杂

promise原理?jQuery的ajax返回的是promise对象吗

解决异步编程的一种方 案,promise内部有三个状态,分别是pending , fulfilled 和 rejected . pending是对象创建后的初始状态,当对象fulfill(成功)时变为fulfilled, 当对象reject(失败)时变为rejected。且只能从pengding变为fulfilled或rejected

jQuery的ajax返回的是promise对象,但是在jQuery中,不仅只有Ajax函数(.ajax,.get, .post)可以返回Promise对象,动画函数也可以返回Promise对象

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

问题:如何进行异常处理?
参照promise的文档我们可以在reject回调和catch中处理异常。但是promise规定如果一个错误在reject函数中被处理,那么promise将从异常常态中恢复过来。这意味着接下来的then方法将接收到一个resolve回调。大多数时候我们希望发生错误的时候,promise处理当前的异常并中断后续的then操作。

web动画几种常见方式

css动画:

优点:浏览器可以对动画进行优化,代码相对简单,性能调优方向固定,对低版本浏览器可以自然降级

缺点:运行过程控制较弱,无法附加事件绑定回调函数,代码冗长

js动画:

优点:控制能力较强(开始,暂停,回放…),比css3动画丰富,css3有兼容性问题,js大多数时候没有

缺点:主线程其他任务干扰出现阻塞丢帧,代码复杂度高于css动画

总结:简单状态切换,不需中间控制,优先使用css动画

post提交数据几种常见Content-Type?

HTTP请求状态码

  • 200 - 请求成功
  • 301 - 资源(网页等)被永久转移到其它URL
  • 404 - 请求的资源(网页等)不存在
  • 500 - 内部服务器错误

正则匹配验证用户输入正确邮箱格式

符号   说明
.   代表除换行符以外的任意字符
\w  代表字母或数字或下划线或汉字
\s  代表任意的空白符
\d  代表数字
\b  代表单词的开始或结束
^   代表字符串的开始
$   代表字符串的结束*   重复零次或更多次
+   重复一次或更多次
?   重复零次或一次
{n} 重复n次
{n,}    重复n次或更多次
{n,m}   重复n到m次var sletter=document.f1.letter.value; //获取表单对象的值if(sletter!=""){var reg = /^([a-zA-Z0-9_-])+@([a-zA-Z0-9_-])+((\.[a-zA-Z0-9_-]{2,3}){1,2})$/;isok=reg.test(sletter);}if (!isok) {alert("邮箱格式不正确!");return false;}

路由hash和history模式

hash 模式是一种把前端路由的路径用井号 # 拼接在真实 URL 后面的模式。hash 也 称作 锚点,本身是用来做页面定位的。当井号 # 后面的路径发生变化时,浏览器并不会重新发起请求,而是会触发 hashchange 事件。

优点:

  1. 兼容性较好(兼容IE8)
  2. hash发生变化的url都会被浏览器记录下来

history模式: API 是 H5 提供的新特性,允许开发者直接更改前端路由,即更新浏览器 URL 地址而不重新发起请求。history api可以分为两大部分,切换和修改,参考MDN,切换历史状态包括back、forward、go三个方法,对应浏览器的前进,后退,跳转操作
优点:

路由正规且无井号#
和hash模式比较,hash 本来是拿来做页面定位的,如果拿来做路由的话,原来的锚点功能就不能用了。其次,hash 的传参是基于 url 的,如果要传递复杂的数据,会有体积的限制,而 history 模式不仅可以在url里放参数,还可以将数据存放在一个特定的对象中。
缺点:

兼容性不如hash模式,兼容到IE10

vuex

为啥出现vuex,解决什么问题

  • 多个视图依赖于同一状态。
  • 来自不同视图的行为需要变更同一状态。
  • Vuex 主要有四部分:
    1. state:包含了store中存储的各个状态。
    2. getter: 类似于 Vue 中的计算属性,根据其他 getter 或 state 计算返回值。
    3. mutation: 一组方法,是改变store中状态的执行者,只能是同步操作
    4. action: 一组方法,其中可以包含异步操作

虚拟DOM

真实dom 操作引起的浏览器的回流和重绘,使得性能开销巨大

虚拟 dom 对象( js 对象),以对象嵌套的方式来表示 dom 树及其层级结构,那么每次 dom 的更改就变成了对 js 对象的属性的增删改查,这样一来查找 js 对象的属性变化要比查询真实 dom 树的性能开销小。

将虚拟节点渲染到视图上****通过patch 的核心----diff 算法,找出本次DOM需要更新的节点来更新

微任务,宏任务

  • 宏任务:setTimeout、setInterval, Ajax,DOM事件
  • 微任务:Promise async/await
  • 微任务执行时机比宏任务要早

为什么微任务执行时机比宏任务要早?

宏任务:DOM渲染后触发,如setTimeout
微任务:DOM渲染前触发,如Promise

如何定义一个方法,把一个视频的一帧生成预览图

重放攻击,列举几种常见防御手段

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-oVwGlelx-1622632598979)(C:\Users\Administrator\AppData\Roaming\Typora\typora-user-images\image-20210426234424609.png)]

JS 主线程拥有一个 执行栈(同步任务) 和 一个 任务队列(microtasks queue),主线程会依次执行代码,下面是JS的异步执行机制
- 当遇到函数(同步)时,会先将函数入栈,函数运行结束后再将该函数出栈;
- 当遇到task任务(异步)时,这些 task 会返回一个值,让主线程不在此阻塞,使主线程继续执行下去,而真正的task任务将交给 浏览器内核 执行,浏览器内核执行结束后,会将该任务事先定义好的回调函数加入相应的**任务队列(microtasks queue/ macrotasks queue)**中。
- 当JS主线程清空执行栈之后,会按先入先出的顺序读取microtasks queue中的回调函数,并将该函数入栈,继续运行执行栈,直到清空执行栈,再去读取任务队列。
- 当microtasks queue中的任务执行完成后,会提取 macrotask queue 的一个任务加入 microtask queue, 接着继续执行microtask queue,依次执行下去直至所有任务执行结束。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-YIWRmsif-1622632598982)(C:\Users\Administrator\AppData\Roaming\Typora\typora-user-images\image-20210424084137746.png)]

函数防抖、截流的区别和使用场景分别是什么?

防抖 一个频繁触发的函数,在规定时间内,只让最后一次生效,前面的不生效。

应用场景

登录、发短信等按钮避免用户点击太快,以致于发送了多次请求,需要防抖
调整浏览器窗口大小时,resize 次数过于频繁,造成计算过多,此时需要一次到位,就用到了防抖
文本编辑器实时保存,当无任何更改操作一秒后进行保存
mousemove、mouseover鼠标移动事件防抖
搜索框搜索输入。只需用户最后一次输入完,再发送请求防抖
手机号、邮箱验证输入检测

节流 一个频繁触发的函数,在规定时间内,函数执行一次后,只有大于设定的执行周期后才会执行第二次。

应用场景

  1. scroll 事件,滚动监听事件,每隔一秒计算一次位置信息等
  2. 浏览器播放事件,每个一秒计算一次进度信息等
  3. input 框实时搜索并发送请求展示下拉列表,每隔一秒发送一次请求 (也可做防抖)
  4. 高频点击提交,表单重复提交

相同点:

都可以通过使用 setTimeout 实现。
目的都是,降低回调执行频率。节省计算资源。

不同点:
函数防抖,在一段连续操作结束后,处理回调,利用clearTimeout 和 setTimeout实现。
函数节流,在一段连续操作中,每一段时间只执行一次,频率较高的事件中使用来提高性能。
函数防抖关注一定时间连续触发的事件只在最后执行一次,而函数节流侧重于一段时间内只执行一次。

async/await 是什么?

async用于声明一个函数是异步的

通常async、await都是跟随Promise一起使用的。因为async返回的都是一个Promise对象

await得到Promise对象之后就等待Promise接下来的resolve或者reject

async 函数返回的是一个promise 对象,如果要获取到promise 返回值,我们应该用then 方法, 继续修改代码

使用async、await完成异步操作代码可读与写法上更像是同步的,也更容易让人理解

解决回调地狱问题

$.set 的作用是什么?

如果我们在创建实例以后,再在实例上绑定新属性,vue是无法进行双向绑定的。

原因是:vue.js的属性必须在 data 对象上才能让 Vue.js 转换它,才能让它是响应的。这里就可以使用this.$set了
 this.$set(this.student,"age", 24)
第一个参数:改变的对象
第二个参数:改变的对象中的属性
第三个参数:改变的属性值

点击按钮下载一个文档到本地

【已经确定路径的单一文件】
(直接页面打开,部分文件类型好像实现不了)

templateUpload(){//下载模板
window.open(this.$app_config.api_host +’/excel/daoruyuangong.xlsx’)
}

方法三(其他情况)
【(利用a标签实现)利用可传参的接口】

downLoad(id){
let a = document.createElement(‘a’)
a.href = this.config.uploadURL+"/api/activitiesPhotoResources/download?id="+id
a.target = ‘_blank’//在新窗口打开
a.click();
},

方法四
【写在html里的】

下载

element-UI

文件的下载

<el-button ``class``=``"import-btn"` `@click=``"handleDownListModelClick"``>下载模板</el-button>

直接通过点击事件来触发需要下载的接口地址

需要注意的是,如果对接的后端接口没有进行二进制数据处理,则需要在请求头中添加

responseType = ``'blob'` `// 与headers是平级的

通过点击事件–调用接口请求,返回对应的二进制编码,(有可能接口已经处理过),那直接转换成我们需要的下载URL即可

// 下载模板async handleDownListModelClick () {try {const res = await this.$store.dispatch('rights/downloadListModel')console.log(res)<br>        // 接口未处理二进制// const blob = new Blob([res.data], {//   type: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet'// })const downloadElement = document.createElement('a')const href = window.URL.createObjectURL(res) // 创建下载的链接downloadElement.href = hrefdownloadElement.download = `模板.xlsx` // 下载后文件名document.body.appendChild(downloadElement)downloadElement.click() // 点击下载document.body.removeChild(downloadElement) // 下载完成移除元素window.URL.revokeObjectURL(href) // 释放掉blob对象if (res) {this.$message({type: 'success',message: '下载成功'})}} catch (err) {console.warn(err)}},

乱七八糟的各式各样的面试题相关推荐

  1. 面试题总结(持续更新中~)

    面试题总结 1.说说你对react的理解?有哪些特性? 2.React组件之间如何通信? props传参: pub-sub传参: context传参: redux 3.说说React生命周期有哪些不同 ...

  2. java面试题2019 答案

    Java 面试随着时间的改变而改变.在过去的日子里,当你知道 String 和 StringBuilder 的区别(String 类型和 StringBuffer 类型的主要性能区别其实在于 Stri ...

  3. Java 最常见的 10000+ 面试题及答案整理:持续更新

    Java面试题以及答案整理[最新版]Java高级面试题大全(2021版),发现网上很多Java面试题都没有答案,所以花了很长时间搜集,本套Java面试题大全,汇总了大量经典的Java程序员面试题以及答 ...

  4. Java后端Java面试题总结2021(春招+秋招+社招)

    Java常见2021年最新面试题,附答案解析 01. 创建socket通讯的步骤? 02. Java 中 sleep 方法和 wait 方法的区别? 03. 程序计数器(线程私有) 04. 什么是线程 ...

  5. 经典面试题:ES如何做到亿级数据查询毫秒级返回?

    点击上方"方志朋",选择"设为星标" 回复"666"获取新整理的面试文章 来源:8rr.co/5Csc 面试题 es 在数据量很大的情况下( ...

  6. 面试题;40个多线程的问题 背1 有用

    Java多线程分类中写了21篇多线程的文章,21篇文章的内容很多,个人认为,学习,内容越多.越杂的知识,越需要进行深刻的总结,这样才能记忆深刻,将知识变成自己的.这篇文章主要是对多线程的问题进行总结的 ...

  7. 硬不硬你说了算!近 40 张图解被问千百遍的 TCP 三次握手和四次挥手面试题

    来自:小林coding 每日一句英语学习,每天进步一点点: 前言 不管面试 Java .C/C++.Python 等开发岗位, TCP 的知识点可以说是的必问的了. 任 TCP 虐我千百遍,我仍待 T ...

  8. 史上最全 Java 多线程面试题及答案

    这篇文章主要是对多线程的问题进行总结的,因此罗列了40个多线程的问题. 这些多线程的问题,有些来源于各大网站.有些来源于自己的思考.可能有些问题网上有.可能有些问题对应的答案也有.也可能有些各位网友也 ...

  9. 耗时118天爆肝【1296页】的“Android高级开发面试题”,终于成功上岸字节

    前言 本人16年毕业于一家普通二本,考研裂开了且没有实习经验,只做过两个项目,每天就是不断地投简历.刷面经,感觉自己都要抑郁了,最后勉强进入了一家学校合作的互联网公司,后面陆陆续续也换了几家公司,毕业 ...

最新文章

  1. AI芯片进入新阶段 哪种企业能胜出?
  2. Bootstrap模态框垂直高度居中问题
  3. 前端学习(1967)vue之电商管理系统电商系统之切换面板获取
  4. linux线程引起jvm崩溃,JVM宕机分析
  5. 编写一个学生类 student,包含的属性有学号、姓名年龄,将所有学生存储在一个数组中
  6. 【网络】tcp三次握手协议
  7. [C++]出错member access into incomplete type
  8. JavaScript之全局函数详解
  9. 归并排序 Java实现 简单易懂
  10. Super Enhancer(超级增强子)分析——ROSE包(v1.3.1)的安装及使用详解
  11. 养肾=养命!这5个养肾方法,程序员都保存好了!
  12. k30s,MIUI12.5开发版线刷为稳定版12.0.3
  13. oracle中转换函数,Oracle中的转换函数
  14. 程序员跳槽全攻略(路漫漫其修远兮)
  15. QVGA HVGA WVGA VGA
  16. 21.深入浅出:直流电源的组成_单相整流滤波电路——参考《模拟电子技术基础》清华大学华成英主讲
  17. Last login: Wed Aug 24 17:23:14 2016 from wr702n.mshome.net
  18. 米斯特WEB安全攻防白帽子培训视频教程 网站安全检测培训教程 第二期
  19. Vue项目设置导航栏高亮
  20. window.onload使用方法

热门文章

  1. mysql的时区问题
  2. Unity实战(2):模型导入Unity
  3. 基于SpringBoot的留守儿童爱心网站
  4. 【请收下这份汇总全网的Java视频资料】
  5. 毕业后4个月,我从待业青年,成功进入国企
  6. 算法学习笔记10——应用哈夫曼树构造最短的不等长编码方案
  7. 开发框架-Web-.Net:NFine
  8. 批处理之find和findstr
  9. selenium自动化测试框架——建议收藏
  10. 发生了COMException 异常来自 HRESULT:0x80040228