博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
近期面试题整理
阅读量:6946 次
发布时间:2019-06-27

本文共 5901 字,大约阅读时间需要 19 分钟。

面试题目,结合网络上的内容参考并总结,会持续更新到找到工作为止,如果有疑问或者错误,欢迎提出.

css样式优先级:

行内样式>内联样式>外链样

css选择器工作模式:

从右向左匹配 从左向右匹配看似高效,其实会把前一次匹配后的每一个后代都要遍历一遍,它的范围是逐渐变大的,否则就有可能遗漏.而从右向左匹配是先匹配最末端的选择器,这样再次匹配的时候只需要去找匹配到的选择器的父级就可以了,这样它的范围是逐渐变小的.

同源策略:

协议,域名和端口都相同时成为一个域,其他域的脚本无法访问除了本域意外的内容.这就是同源策略,有了这个策略,网络才相对的安全.同时我们也可以使用一些手段来进行跨域请求,比如:

  1. cors跨域资源共享:通过在请求中添加一个Origin字段,表示需要跨域请求的地址,如果服务器端允许这个域访问,响应头里就会有Access-Control-Allow-Origin字段,表示同意请求.

它分为简单请求和非简单请求: 简单请求:HEAD,GET,POST 并且请求头里不超出一下几种字段:

Accept

Accept-Language

Content-Language

Last-Event-ID

Content-Type:只限于三个值application/x-www-form-urlencoded、multipart/form-data、text/plain

非简单请求:PUT,DELETE,或者content-typeapplication/json的请求

非简单请求会先发送一个试探的请求OPTIONS,同样请求头要有Origin,并且加上Access-Control-Request-MethodAccess-Control-Request-Headers,服务器对试探请求相应成功后响应头上会有Access-Control-Allow-Origin字段,接下来的请求就会和简单请求一样了.

跨域资源共享的内容参考了阮一峰大大的文章

  1. JSONP:利用script标签的src属性没有跨域限制的特点,在需要跨域请求的时候动态生成一个script标签,src属性为需要跨域的地址,并且提供一个回调函数来接受数据,然后服务器会返回jsonp的包装,形如callback({...}),然后浏览器就会电泳callback回调函数,并且把解析后的json对象作为参数,然后就可以在这个回调函数里处理请求到的数据,只能使用get方法,并且本地的回调函数需要在全局作用域下.
  2. window.name
  3. domain
  4. iframe
  • 什么时候才会有跨域的需求? 前端和后端使用不同的端口时,属于不同域,不在同源策略之内,这是需要进行跨域相关的配置.

浮点数计算

参考地址:

0.1+0.2=0.30000000000000004

js中的数字采用的是64位的双精度浮点数,它的最高位表示符号,接着11位表示指数,余下的52位为有效数字. 符号位决定的数字的正负,指数部分决定了数值的大小,有效数字部分表示精度

这里要提一下二进制如何表示小数.

  • 就比如这个0.1.
  1. 取它的小数部分,当然就是0.1了,乘2得到0.2,这是取它的整数部分第一位表示二进制小数的第一位(0).
  2. 再乘2,得0.4,取整数部分第一位(0),得到二进制小数的第二位(0).
  3. 再乘2,得0.8,取整数部分第一位(0).得到二进制小数的第三位(0).
  4. 再乘2,得1.6,取整数部分第一位(1),得到二进制小数第四位(1).
  5. 依次类推,会发现,0.1的二进制小数是这样的:

0.0001 1001 1001 1001....(无限循环)

  • 而0.2的二进制小数为:

0.0011 0011 0011 0011....(无限循环)

而js遵循IEEE754标准的64位双精度浮点数的小数部分最多只支持53位二进制位,所以0.1和0.2的二进制数相加如下:

0.1 : 0.0001 1001 1001 1001 1001 1001 1001 1001 1001 1001 1001 1001 1001

0.2 : 0.0011 0011 0011 0011 0011 0011 0011 0011 0011 0011 0011 0011 0011

结果: 0.0100 1100 1100 1100 1100 1100 1100 1100 1100 1100 1100 1100 1100

  • 这里再将结果转换成十进制数:

0+(0 * 2^-1)+(1 * 2^-1)+(0 * 2^-3)+(0 * 2^-4)+(1 * 2^-5)+(1 * 2^-6)+(0 * 2^-7)+(0 * 2^-8)...(总共52位)

最终得到的结果0.30000000000000004,所以在进行算数计算的时候就会产生误差.

那么如何消除这种误差呢?

有效数字最多可以表示53位二进制数,也就是2^53=9007199254740992,对应的科学计数法为9.007199254740992e+16,这也是js最多能表示的精度,它的小数部分长度为16.

所以我们可以使用toPrecision方法来做精度计算,超过的精度胡自动做凑整处理比如0.30000000000000004.toPrecision(16)=0.3000000000000000,去掉末尾的0后正好是0.3

其实在整数中也同样存在着精度问题:我们知道js能表示的最大数字(2^53 - 1,Number.MAX_SAFE_INTEGER,9007199254740991)最小数字(-(2^53 - 1),Number.MIN_SAFE_INTEGER,-9007199254740991)

超过了这个范围的数字的计算就会不准确,但是我们可以通过引入插件来解决,比如bignumber.js之类的,原理是用过把数字当作字符串,重新实现计算的逻辑,缺点就是性能比原生差很多.

toPrecisiontoFixed的区别?

  • toPrecision是处理精度,精度是从左至右第一个不为0的数开始数起.
  • toFixed是小数点后指定位数取整,从小数点开始数起.

遇到浮点数误差问题时可以直接使用 https://github.com/dt-fe/number-precision 完美支持浮点数的加减乘除、四舍五入等运算。

前端页面优化

http请求优化

  1. 减少http请求
  • 首先是压缩,合并js,css文件,可以配置webpack使其合并成一个唯一的出口文件.
  • 延迟加载 适合延迟加载的东西很多,最需要的当然是图片.原理就是首先将要延迟加载的图片src替换为空白或者指定的loading图,当达到指定条件的时候再将真是图片的资源路径替换到src属性上让浏览器去加载. 首屏可是使用定时器,其他屏可以通过当前元素的位置,和滚动的距离来判断是否需要加载图片
  • 雪碧图 在容器元素上设置background-image属性,在子元素上设置background-position属性来确定其位置
  1. 预加载 延迟加载的目的是为了减少不必要的请求,用户有需求的时候才去请求资源,而预加载是预先判断需要加载的数据,预先加载,并且在达到指定条件之后直接从浏览器缓存中获取
  2. 静态资源使用单独的域名和服务器 将静态资源放在额外的服务器上和域名上,这样主域名就可以减少http请求数,减少主服务器的带宽使用,主服务器就可以更快的响应请求.
  3. http缓存 http缓存策略可以把未过期或者未更改的资源重复使用,同样也可以减少服务器的带宽使用.
  4. ajax局部加载 在达到某些条件后,可以使用ajax刷新局部页面,这样也可以减少不必要的请求.

页面/性能优化

  1. 引用优化

将css文件放在html文档的head标签内,将js文件放在body标签的最下面.

css文件时异步加载的,浏览器构建dom树的同时如果有对应的css样式就是直接渲染出来,这样会让样式更早的呈现在页面上.

而js文件下载的时候会阻塞dom数的构建,只有js下载完成后才会继续构建接下来的dom树,将js文件放在最下面可以在视觉上减少白屏的现象.

  1. 将js动画替换成css动画

主流浏览器已经全部支持的css3

在js中使用动画是利用定时器循环改变dom元素的位置来达到动画效果,这样会造成浏览器的回流,会影响前端页面的性能,如果一定要使用js实现动画,可以在动画之前使其脱离正常文档流,在动画结束之后再让其回归文档流.

而使用css3动画后,在性能上,浏览器会新建一个图层来运行动画,并且可以使用硬件加速.在效果上js动画的最小移动单位为1px,而css3动画可以打破这个束缚,让动画看起来更加流畅.

http缓存策略

http缓存是减少http请求,减少请求带宽,增加页面访问速度的有效办法.

http缓存主要依靠http报文中的字段来判断是都对数据进行缓存.

  • 首先是强缓存:
  1. 通过cache-control设置max-age=[秒]来设置一个资源的最大保存事件,他是一个相对事件,意思是存请求成功之后的n秒之内,浏览器都直接从本地获取已缓存的资源.

  2. expires:服务器通过设置expires响应头,值为一个格林尼治时间,属于绝对时间,可以告诉浏览器缓存过气的时间,在这个过气事件之前,再次请求的数据都来自本地,在这个时刻之后才会向服务器请求资源.

expires有一个漏洞,就是他设置的过期事件是需要和本地操作系统的时间进行对比的,如果更改了本地的时间,那么这个对比就会不准确,而max-age则不会出现这样的问题,通常为了兼容http1.0会将expires和max-age同时设置,在同时设置后,浏览器会优先匹配max-age的规则.

  • 协商缓存
  1. last-modified:服务器在第一次接收到请求的时候,可以设置一个last-modified字段,用来保存这个资源的最后更改日期,浏览器接收到响应后,再次请求的时候,会自动在请求头中添加if-modified-since字段,它的值就是第一次响应时的last-modified的值,然后后台通过判断这个值与文件最后修改时间是否相同,如果相同,则可以返回304状态码提示浏览器使用缓存中的数据,如果不同则重新设置last-modified的时间,并返回最新数据.

  2. ETag:服务器在相应请求的时候通过某种算法,给资源计算出一个唯一的标识符,在相应请求的时候会带上这个标识符,放在ETag字段上,而浏览器在下次请求的时候会自动带上一个If-None-Match字段,值就是第一次请求时的ETag字段的值,服务器通过鼻尖请求头中If-None-Match的值和服务器上资源的ETag值,如果匹配则返回304状态码,提示浏览器直接使用本地缓存,如果不匹配则重新下载资源.

在以几个字段同时设置的情况下,会先使强缓存策略生效,如果强缓存过期了,才会使用协商缓存策略,而如果协商缓存策略也同时失效,才会重新下载资源.

  • 还有一个问题如果强缓存和协商缓存都未失效,而我们又想让浏览器更新资源,这是该怎么做?

可以通过设置url上的querystring来解决,一般有两种解决方式:

  1. 使用版本号,比如http://url.com?version=20180201
  2. 使用hash值,比如http://url.com/?hash=sdfkljlkjasdklxclkv13

这样浏览器就会从服务器更新资源.

原型链

  • 原型基础知识:
  1. 每个构造函数上都有个prototype属性 ,prototype是一个对象
  2. prototype对象上有一个constructor属性,这个属性指向当前的构造函数
  3. 每个对象上都有一个__proto__属性,这个属性指向所属类的原型
  • 属性和方法查找顺序
  1. 若已找到私有的属性和方法,则不会再向原型上继续查找
  2. 若未找到私有属性和方法,则通过__proto__去当前实例所属类的原型上查找
  3. 若还未找到,则继续通过__proto__继续往上级(父类)查找,直到找到Object类的原型上

若都没有找到,则返回undefined(查找对象的属性和方法,如果没有这个方法返回的是undefined,不是报错) Object类是所有类型的基类,其他类为Object的派生类

  • 原型链
  1. 通过__proto__属性一级一级的往父类上查找,就形成了一个原型链 __proto__属性是实现原型继承的关键

ie中因安全考虑 禁止手动操作__proto__属性

继承

  1. 原型链继承:直接让子类的prototype属性指向父类的实例,这样在子类的原型上拥有了父类的私有和公有属性.
  2. 借用构造函数(经典继承):在子类的构造函数中使用父类.call(this)方法,在构造新的子类实例的时候其实也执行了父类的初始化代码,并且改变了this指向,这样子类就可以使用父类的私有属性了
  3. 原型式继承Object.create():create函数内部创建了一个临时的中间类,让这个类的原型等于传进来的原型对象,最后返回了这个中间类的实例,让子类的prototype属性等于返回的实例,这样就拿到了父类的公有方法.

作用域链

  • 全局作用域:浏览器加在页面时形成,谁都可以访问,全局下定义的变量是全局变量
  • 私有作用域:函数运行时形成,只有自己可以访问,私有变量:带var关键词和形参

变量的查找: 1.先看是否是私有的,如果是私有的(带var或形参)则就是它 2.如果不是私有的则往上级作用域查找,如果还没找到则继续往上级作用域查找,直到找到window下,

  • 通过函数形成的作用域一级一级的向上查找,就形成了作用域链

若window下也没有则会报错 Uncaught ReferenceError: xxx is not defined

上级作用域:在哪定义的,上级作用域就是谁

项目中大量的静态资源如何处理

  1. 静态资源如js,css尽可能合并,图片合成单张雪碧图,减少http请求次数.
  2. 使用单独的域名和服务器来储存静态资源,并设置缓存策略,这样主服务器可以只接受业务请求,可以有效分流,主服务器可以更快的相应.
  3. 直接使用CDN服务,将静态资源保存在cdn服务器中,不同地区的用户访问网站时,cdn服务器会查找最近的拥有静态资源的服务器并返回资源,达到访问加速的目的,并且cdn服务器也很安全,可以有效防止攻击.

转载地址:http://zmonl.baihongyu.com/

你可能感兴趣的文章
IP数据包的分析实例
查看>>
HTML中head头结构
查看>>
Python 后台基于 PackerNg 格式动态生成 APK 渠道包
查看>>
笔记:非阻塞读终端和等待超时
查看>>
sublime2 text编辑器最新使用技巧
查看>>
Ionic3--禁用页面返回按钮
查看>>
软件版本定义【转、原】
查看>>
微服务架构设计基础之立方体模型
查看>>
linux通过Git快速部署项目
查看>>
CDN a,b,c三种鉴权的PHP代码
查看>>
Else从句
查看>>
DIV盒子模型理解的总结
查看>>
win7始终以管理员权限运行软件
查看>>
percona-server-5.6.25-73.1安装笔记---配置篇
查看>>
Function和function
查看>>
java socket 注意的地方
查看>>
Oracle11gR2DataGuardSetupusingOracleGridControl
查看>>
Android 之 JNI 开发 详解 - NDK从入门到精通
查看>>
pyspider爬虫学习-教程1-HTML-and-CSS-Selector.md
查看>>
乐视秒杀:每秒十万笔交易的数据架构解读
查看>>