- [] == [] 输出的结果是?为什么?
[][]输出的结果为false;
首先,‘’运算符比较的是两个操作数是否相等,(这里不是指严格相等),两个操作数都是空数组,都是Object对象。但是对象的比较并非是值得比较,即使这两个都是空数组(包含同样的属性和数值都为空),但是这两个数组在引用上都不是同一个数组,所以他们也是不相等。
这就涉及到不可变的原始值和可变的对象引用、以及‘’运算符和‘=’运算符对于对象的比较规则的知识点。
2.请说出三种减少网页加载时间的方法。
- CDN加速
- css使用精灵图
- 使用图片懒加载
服务器角度
采取CDN加速
开启gzip压缩
允许使用强缓存或协商缓存
增加服务器带宽
客户端角度
合理组织CSS、JavaScript代码位置
减少DOM操作、添加事件委托
部分操作可设置防抖和节流
对于可预见的操作采取preload或prerender的预加载
对于图片可以懒加载
合并CSS图片(精灵图/雪碧图)
减少使用iframe
资源优化打包角度
使用打包工具将Js文件、CSS文件和静态文件进行恰当打包处理。
比较好理解的:
-
减少http请求,特别是vue在请求http时,要将请求放在父组件中,不然每个子组件都去请求一遍就很浪费性能
-
CSS写在顶部,JavaScript写在尾部或异步
-
延时加载图片懒加载
-
使用iconfont
-
使用CDN
-
使用缓存,在vue中可以使用keep-alive,这样重复访问一个页面时就不会重新去请求,而是从缓存中取出来直接使用。
3.请问什么情况下会遇到跨域问题?
当协议,端口,域名任意一个不同时。就会出现跨域问题。
jsonp,CORS可以解决此问题
4.http协议中与资源缓存相关的协议头有哪些?
通用首部:
Cache-Control:HTTP/1.1+控制缓存的协议头
pragma:HTTP/1.1之前控制缓存的协议头
实体头部:
expries:实体主题过期的日期,后面直接跟一个缓存失效日期
5.CSS中box-sizing有哪些值?区别是什么?
默认值:content-box:设置的width和height只包括了内容,不包括padding,border,margin
border-box:设置的width和height包括了content,padding和boder。但是不包括margin
6.DOM Tree与Render Tree之间的区别是什么?
DOM tree包含了所有的HTML节点的树,包括display:none,JS动态添加的元素等
DOM tree和CSSOM tree结合后组成了Render tree。DOM树和渲染树都是浏览器生成的
7.在Javascript中什么情况下会进行装箱/拆箱转换?
装箱:基本数据类型转换成引用数据类型
拆箱:引用数据类型转换成基本数据类型
当引用数据类型和基本数据类型需要转换时进行装箱/拆箱
写出下列代码的执行结果:
new Promise((resolve) => {
console.log('1')
resolve()
console.log('2')
}).then(() => {
console.log('3')
})
setTimeout(() => {
console.log('4')
})
console.log('5')
- 执行宏任务 输出1,2,then放进微任务队列
- 遇到setTimeout,放进宏任务队列,继续执行,输出5
- 执行then,输出3
- 没有微任务了,执行宏任务,输出4
最后输出结果:1 2 5 3 4
请列举几个HTML5语义化标签,并说说语义化有什么优点?
<header>顶部标签</header>
<nav>导航栏标签</nav>
<section>中心标签(用作主体的包裹)</section>
<article>文章标签</article>
<footer>底部页脚信息标签</footer>
<dialog>会话框标签</dialog>
优点:
代码结构清晰,方便阅读,有利于团队合作开发。
方便其他设备解析(如屏幕阅读器、盲人阅读器、移动设备)以语义的方式来渲染网页。
有利于搜索引擎优化(SEO)。
请列举几种除了px外的CSS度量单位并解释其含义。
rem(root em) 相对于html根节点的字体大小,1rem等于html里font-size的大小;
em 与rem相似,不过是相对于父元素的字体大小;
vh 和 vw 表示屏幕大小单位
new操作符做了什么?
简单点来说,new操作符会先创建一个空对象,然后将this指向这个空对象,并且进行赋值,最后返回这个this。
function create(){
// 1. 创建空对象
let obj = new Object();
// 2. 链接原型
let con = [].shift.call(arguments)
obj.__proto__ = con.prototype
// 3. 绑定this
let res = con.apply(obj,arguments)
// 4. 返回新对象
return typeof res === 'object'?res:obj;
}
var func = function(){}
var newO = new func()
new一共经历了四个阶段
1.创建了空对象
var newO = new Object()
2.设置原型链
newO,proto = func.prototype
3.将func中的this指向newO
var result = func.call(newO)
4、判断Func的返回值类型:
如果是值类型,返回obj。如果是引用类型,就返回这个引用类型的对象
简述cookie/session记住登录状态机制原理。
cookie是缓存在浏览器中的,在第一次http请求时就夹带在里面,然后只要cookie不过期,就会一直保留
session是缓存在内存中,即 将登录信息存放在电脑的内存中。
网页中接收事件的顺序(事件流)有哪些?它们之间的区别是什么?
有捕获和冒泡两种,
冒泡是事件由子元素传递到父元素的过程.
捕获是时间由父元素传递到子元素的过程
冒泡阶段调用事件处理函数
封装一个getTag函数,当点击a标签的时候,由于是冒泡机制,会从目标节点向上逐级触发各个节点a,li,ul,div的事件处理函数。
捕获阶段调用事件处理函数
在function回调函数里加个true,则为事件捕获。当点击a标签的时候,由于是捕获机制,会从根节点向下逐级触发各个节点直到目标节点触发事件处理函数即div,ul,li,a
简述你对HTTP控制访问(CORS)的理解。
首先要搞明白什么是同源,什么是跨域。
打一个简单的比方,你自己从你家里拿东西,不会有人说,这是同源;但是你要从隔壁的邻居的冰箱去拿可乐,你觉得可能吗,这就是跨域。
从比方中回来,事实其实没有那么简单。理解了概念后,得知道如何去判断同源还是跨域。web服务器有三要素:协议(http、https)、端口号(不过多说)、web服务器域名(比如https://github.com/mamba666
中https://github.com就是域名)。三要素必须全部一致才算同源
个人认为写完上面的东东后已经理解了同源跨域已经如何区分。接下来就来看看真正的干货,不讲同源,只讲跨域(以下参考MDN)
浏览器端
如果发现有一个请求是跨域,那么浏览器会自动先拦截一下,给它的http header加上Origin字段。比如 http://localhost:8080变为Origin:http://localhost:8080。这样一来,服务器端就可以区分这个请求是不是跨域了。
服务器端
当服务器端收到浏览器端发送过来的请求后,会有一个响应header。它会告诉请求的浏览器哪儿些域名可以请求我,哪儿些方法可以执行。
响应回到浏览器端
此时浏览器会根据这个响应自动判断,然后在做决定。
服务器端返回给浏览器端的东西
Access-Control-Allow-Origin 允许跨域的Origin列表
Access-Control-Allow-Methods 允许跨域的方法列表(GET、POST等)
Access-Control-Allow-Headers 允许跨域的Header列表
Access-Control-Expose-Headers 允许暴露给JavaScript代码的Header列表
Access-Control-Max-Age 最大的浏览器缓存时间,单位为s
跨域请求形式
有两种,简单和非简单请求。这里说说我常遇到的 application/json 。这就是一种非简单请求,在以上所写的浏览器端之前,会先进行一次预请求,根据这个结果再去判断是否正式请求。
其实写了这么多,最重要的就是对CORS的理解,已经这个流程是怎么样的。