原型和原型链

原型

  1. 在 js 中我们是使用构造函数来新建一个对象的,每一个构造函数的内部都有一个 prototype 属性,这个属性是一个对象,这个对象上包含了该构造函数的所有实例共享的属性和方法
  2. 当我们使用构造函数新建了一个对象后,在这个对象的内部包含一个指针 __proto__,这个指针指向该对象所属构造函数的 prototype 属性对应的值, 在ES5 中这个指针被称为 对象 的原型
  3. 一般来说我们是不能够获取到这个值的,但是现在的浏览器都实现了 proto 属性,让我们可以访问这个属性,但是最后不要用这个属性, 因为它不是规范中规定的
  4. ES5 中新增了一个Object.getPrototypeOf()方法,我们可以通过这个方法来获取对象的原型

原型链

  • 当我们访问一个对象的属性时,如果这个对象内部不存在这个属性,那么它就会去它的原型对象里找这个属性,这个原型对象又会有自己的原型,于是就这样一直找下去,这也就是原型链的概念.
  • 原型链的尽头一般来说都是 object.prototype

原型和原型链的特点

  • JavaScript 对象是通过引用来传递的,我们创建的每一个新对象实体中并没有 一份属于自己的原型,当我们修改原型时,与之相关的对象也会继承这一改变

js 获取原型的方法

  • p.__proto__
  • p.constructor.prototype
  • Object.getPrototypeOf(p)

作用域链

  1. 作用域: 当前代码对变量的访问权限(函数作用域,es6 let const 声明的块级作用域)
  2. 作用域链: 内层作用域访问一个变量,首先会在当前作用域的父级找,如果没找到,在往上一层找,直到找到全局,如果还没有找到就宣布放弃,这种一层一层向上的关系,就是作用域链,即以链式的方式访问变量

垃圾回收机制

  • 垃圾回收机制: 会自动释放内存,就是说一个函数执行完毕,内存中的空间会被释放,再一次调用的时候,函数内部会被重新赋值

闭包

闭包的作用

  1. 读取函数内部的变量,让全局访问局部变量
  2. 延长变量的生命周期

    闭包的使用方式

  • 就是函数内部嵌套着另一个函数,这个函数在外部别调用,所以内存不会被回收,从而延长变量的生命周期

什么是递归

  • 递归就是函数自己调用函数自己,递归一定要有结束条件,否则会陷入死循环
  • 使用场景: 遍历树的结构

js的异步机制

详情请看本站文章 《js的异步机制》

事件循环机制(Event Loop)

详情请看本站文章 《事件循环机制Event Loop》

什么是 Promise 对象? 什么是 Promise/A+ ?

  1. promise对象是异步编程的一种解决方案,最早由社区提出,promise/A+规范是javascript promise的规范,规定了一个promise所必须具有的特性
  2. Promise 是一个构造函数,它接收一个函数作用参数, 并且返回一个promise实例,一个promise实例有三种状态,分别是pending,resolve,reject,对应着进行中,已完成,已失败,一个实例的状态只能由 pending 转换为 resolve 或由 pending 转换为 reject ,状态一经改变就凝固了,无法再改变,我们可以在异步操作结束后调用这两个函数改变promise的状态,一个状态一经改变可以通过 then 注册回调函数,可以立即得到结果

ES5 继承和 ES6 继承的区别

实质

  • ES5 的继承实质: 先创建子类,再实例化父类,并将父类的方法添加到子类的this中;可以通过原型或构造函数机制来实现
  • ES6 实质: 先创建父类,实例化子类通过调用super方法访问父类后,在通过修改this实现继承,super关键字指代父类的实例,即父类的this对象,在子类构造函数中,如果不调用super方法,子类得不到this对象
  • ES6 实现继承是通过关键字 extends super 来实现继承

new 的时候做了什么

  1. 首先创建了一个新的空对象
  2. 设置原型,将对象的原型设置为函数的 prototype 对象
  3. 让函数的 this 指向这个对象,执行构造函数的代码,为这个新对象添加属性
  4. 判断函数的返回值类型,如果是值类型,返回创建的对象;如果是引用类型,就返回这个引用类型的对象

详情请看本站文章 《如何实现一个 new》

Ajax是什么? 如何创建一个Ajax?

什么是Ajax

  • AJAX,异步的 JavaScript 和 XML ,是一种实现 无页面刷新 获取数据的 混合技术 ,简单来说就是JavaScript执行异步请求

    Ajax原理

  • 比如,领导要找张三汇报工作,于是领导就委托秘书帮忙去叫张三,然后领导就继续忙自己的工作,直到秘书告诉领导张三到了,接着张三就开始汇报工作
  • AJAX 请求数据的流程 就跟 “领导找张三汇报工作相似” , 其中的核心 就是 秘书,秘书相当于浏览器的XMLHttpRequest对象,当浏览器发出HTTP请求与接收HTTP响应时,浏览器可以接着做其他的事情,直到收到xhr返回的数据渲染页面

AJAX 实现流程

创建一个 ajax 有这样几个步骤

首先是创建一个 XMLHttpRequest 对象。

然后在这个对象上使用 open 方法创建一个 http 请求,open 方法所需要的参数是请求的方法、请求的地址、是否异步和用户的认证信息。

在发起请求前,我们可以为这个对象添加一些信息和监听函数。比如说我们可以通过 setRequestHeader 方法来为请求添加头信息。我们还可以为这个对象添加一个状态监听函数。一个 XMLHttpRequest 对象一共有 5 个状态,当它的状态变化时会触发onreadystatechange 事件,我们可以通过设置监听函数,来处理请求成功后的结果。当对象的 readyState 变为 4 的时候,代表服务器返回的数据接收完成,这个时候我们可以通过判断请求的状态,如果状态是 2xx 或者 304 的话则代表返回正常。这个时候我们就可以通过 response 中的数据来对页面进行更新了。

当对象的属性和监听函数设置完成后,最后我们调用 sent 方法来向服务器发起请求,可以传入参数作为发送的数据体。

AJAX的状态

  • 0 表示未初始化,尚未调用open方法
  • 1 启用open方法,数据发生
  • 2 表示已调用open方法 接收到响应
  • 3 表示正在解析
  • 4 表示已完成

详情请看本站文章 《Ajax》

面向对象

什么是面向对象

  • 面向对象,是一种编程开发思想,面向对象编程,它将真实世界各种复杂的关系,抽象为一个个对象,然后进行分工合作,完成对真实世界的模拟
  • 面向对象的特性: 封装 / 多态 / 继承
  • 面向对象就是对 现实世界理解和抽象的方法
    我对面向对象的理解就是: 面向对象的编程方式就是让每一个类都只做一件事,面向过程会让一个类越来越全能,就像是一个管家一样做了所有的事;而面向对象像是雇佣了一群职员,每个人做一件小事,各司其职,最终合作共赢

JSON.parse()和JSON.stringify()

JSON.parse()把字符串解析成对象
JSON.stringify()从对象中解析出字符串

三种事件模型是什么?

详情请看本站文章 《事件模型》

事件委托

事件委托本质上是利用了浏览器事件冒泡的机制,因为事件在冒泡过程中会上传到父节点,并且父节点可以通过事件对象获取到目标节点,因此可以把子节点的监听函数定义在父节点上,由父节点的监听函数统一处理多个子元素的事件,这种方式称为事件代理

使用事件代理我们可以不不必要为每一个子元素都绑定一个监听事件,这样减少了内存上的消耗,并且使用事件代理我们还可以实现事件的动态绑定,比如说新增了一个子节点,我们并不需要单独第为它添加一个监听事件,它所它发生的事件会交给父元素中的监听函数来处理

执行上下文

执行环境(即执行上下文中)存在着执行代码的的私有作用域,上层作用域的指向,方法的参数,这个作用域中定义的变量以及这个作用域的this对象等等

堆内存和栈内存

基本数据类型: 栈内存 先进后出
复杂数据类型: 堆内存 优先队列,复杂数据类型将值报存在堆中,将值对应的指针保存在栈中,通过栈中的指针来获取堆中的值

模块化开发怎么做

详情请看本站文章 《模块化》

ES6 中新增特性

《ES6 中新增特性》

Promise.all 的实现

Promise.all 同时发送多个请求,并行运行 promise, 所以 promise 成功则返回成功,如果有一个失败,则返回失败,并返回失败的原因

1
2
3
4
5
6
7
8
9
10
11
promise.all = function(promises) {
let res = []
return new Promise(function (resolve) {
promises.forEach(function(val) {
val.then((r) => {
res.push(r)
})
})
resolve(res)
})
}
1