参考 Promise A+ 简单实现 promise,用的setTimeout 模拟的异步,与实际浏览器Promise 有出入(具体可以看Event loop 相关),本文只做思路理解参考。

Promise 的简单实现,主要理解规范,也可以再理解一下几个点方变记忆:

  • Promise的三种状态(pending,fulfilled,rejected), pending状态转移后不可变
  • resolve , resolve a promise with a promise
  • reject
  • Promise.prototype.then 返回一个新的promise 对象(链式操作)
  • thenable对象

1.简单实现

 const PENDING = 'pending'
const FULFILLED = 'fulfilled'
const REJECTED = 'rejected' function needResolve() {
throw new TypeError('need pass function to Promise')
} function needuseNew() {
throw new TypeError(
'Promise is a constructor and should be called with the `new` keyword'
)
} function Promise(task) {
var self = this
this.state = PENDING
this.value
this.fulArr = []
this.rejArr = [] function resolve(value) {
if (value != null && value.then && typeof value.then == 'function') {
return value.then(resolve, reject)
}
setTimeout(() => {
if (self.state == PENDING) {
self.state = FULFILLED
self.value = value
self.fulArr.forEach(item => {
item(self.value)
})
}
})
} function reject(reason) {
setTimeout(() => {
if (self.state == PENDING) {
self.state = REJECTED
self.value = reason
self.fulArr.forEach(item => {
item(self.value)
})
}
})
}
typeof task !== 'function' && needResolve()
!(this instanceof Promise) && needResolve()
try {
task(
function(value) {
resolve(value)
},
function(reason) {
reject(reason)
}
)
} catch (e) {
reject(e)
}
} function resolvePromise(promise, x, resolve, reject) {
if (promise === x) {
return reject(new TypeError('do not resolve promise with itself'))
}
var then, called
// resolve promise with promise
if (x instanceof Promise) {
if (x.status == PENDING) {
x.then(function(y) {
resolvePromise(promise, y, resolve, reject)
}, reject)
} else {
x.then(resolve, reject)
}
// thenable 其它的then
} else if (x !== null && (typeof x == 'function' || typeof x == 'object')) {
try {
// resolve promise with promise
then = x.then
if (typeof then === 'function') {
then.call(
x,
function(y) {
if (called) {
return
}
called = true
resolvePromise(promise, y, resolve, reject)
},
function(r) {
if (called) {
return
}
called = true
reject(r)
}
)
} else {
resolve(x)
}
} catch (e) {
if (called) {
return
}
called = true
reject(e)
}
} else {
resolve(x)
}
}
Promise.prototype.then = function(onFulfilled, onRejected) {
var self = this
onFulfilled =
typeof onFulfilled === 'function'
? onFulfilled
: function(value) {
return value
}
onRejected =
typeof onRejected === 'function'
? onRejected
: function(reason) {
throw reason
}
var promise2
if (self.state == PENDING) {
promise2 = new Promise(function(resolve, reject) {
self.fulArr.push(value => {
try {
let x = onFulfilled(value)
resolvePromise(promise2, x, resolve, reject)
} catch (e) {
reject(e)
}
})
self.reject.push(reason => {
try {
let x = onRejected(reason)
resolvePromise(promise2, x, resolve, reject)
} catch (e) {
reject(e)
}
})
})
}
if (self.state == FULFILLED) {
promise2 = new Promise(function(resolve, reject) {
setTimeout(() => {
try {
let x = onFulfilled(self.value)
resolvePromise(promise2, x, resolve, reject)
} catch (e) {
reject(e)
}
})
})
}
if (self.state == REJECTED) {
promise2 = new Promise(function(resolve, reject) {
setTimeout(() => {
try {
let x = onRejected(self.value)
resolvePromise(promise2, x, resolve, reject)
} catch (e) {
reject(e)
}
})
})
}
// then 必须返回一个新的promise
return promise2
} Promise.prototype.catch = function(onRejected) {
return this.then(null, onRejected)
} Promise.resolve = function(value) {
return new Promise((resolve, reject) => {
resolve(value)
})
}
Promise.reject = function(value) {
return new Promise((resolve, reject) => {
reject(value)
})
} function gen(time, resolve) {
let result = []
let i = 0
return function(index, value) {
if (i < time) {
i++
result[index] = value
} else {
resolve(result)
}
}
} Promise.race = function(arr) {
return new Promise((resolve, reject) => {
for (let i = 0; i < arr.length; i++) {
Promise.resolve(arr[i]).then(resolve, reject)
}
})
}
Promise.all = function(arr) {
return new Promise((resolve, reject) => {
let done = gen(arr.length, resolve)
for (let i = 0; i < arr.length; i++) {
Promise.resolve(arr[i]).then(function(value) {
done(value, i)
}, reject)
}
})
}
module.exports = Promise

webpack基础小结。的更多相关文章

  1. js学习笔记:webpack基础入门(一)

    之前听说过webpack,今天想正式的接触一下,先跟着webpack的官方用户指南走: 在这里有: 如何安装webpack 如何使用webpack 如何使用loader 如何使用webpack的开发者 ...

  2. webpack基础+webpack配置文件常用配置项介绍+webpack-dev-server

    一.webpack基础 1.在项目中生成package.json:在项目根目录中输入npm init,根据提示输入相应信息.(也可以不生成package.json文件,但是package.json是很 ...

  3. 搭建webpack基础配置

    搭建webpack基础步骤: 1.去官方网站下载node.js(根据自己电脑的系统类型选择) 2.安装node.js完成后打开cmd命令提示符: 出现版本号证明安装成功 3.cd到工程目录下 npm ...

  4. Java 基础--小结

    Java  基础--小结 java基础 Java源程序(.java文件)——>java字节码文件(.class文件)——>由解释执行器(java.exe)将字节码文件加载到java虚拟机( ...

  5. nodejs+gulp+webpack基础知识

    nodejs+gulp+webpack基础知识 2019年08月22日 11:49:40 天府云创 阅读数 22   版权声明:本文为博主原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文 ...

  6. Webpack基础学习

    Webpack基础学习:https://segmentfault.com/a/1190000008853009

  7. 学习webpack基础笔记01

    学习webpack基础笔记 1.webpack搭建环境最重要的就是如何使用loader和plugins,使用yarn/npm安装插件.预处理器,正确的配置好去使用 2.从0配置webpack - 1. ...

  8. android基础小结

    (注:此小结文档在全屏模式下观看效果最佳) 2016年3月1日,正式开始了我的android学习之路. 最最开始的,当然是学习怎样搭载环境了,然而苦逼的我在win10各种坑爹的指引下还是安装了一个星期 ...

  9. 【webpack】---模块打包机webpack基础使用---【巷子】

    001.什么是webpack? 作用有哪些? WebPack可以看做是模块打包机:它做的事情是,分析你的项目结构,找到JavaScript模块以及其它的一些浏览器不能直接运行的拓展语言(Scss,Ty ...

随机推荐

  1. 你不知道的CSS单位

    CSS中大部分属性值都有对应的量词单位,常见的如描述盒模型尺寸的 width, height, margin, padding, border,又比如CSS3中的transform属性的一些值.下面的 ...

  2. Laravel日常使用总结

    字段当做键值key 集合的keyBy()方法详情:戳这里 创建模型类和数据库迁移文件 php artisan make:model Post -m 创建控制器和基础的方法 php artisan ma ...

  3. aspnet mvc 中 跨域请求的处理方法

    ASP.NET 处理跨域的两种方式    方式1,后端程序处理.原理:给响应头加上允许的域即可,*表示允许所有的域                 定义一个cors的过滤器 加在在action或者co ...

  4. Python 30分钟快速入门指南

    学习地址 中文版:Python 30分钟入门指南 英文版:Learn X in Y minutes 学习时间 2019/03/10 19:00 - 19:32,多用了2分钟.

  5. webpack打包样式代码去重

    一.问题描述 控制台审查样式,同一个样式被导入很多遍,每调用一次@import "common.less";打包时都会多出一份类似的样式代码. 二.问题分析 补上... 三.解决方 ...

  6. Django与Celery配合实现定时任务

    一.前言 Celery是一个基于python开发的分布式任务队列,而做python WEB开发最为流行的框架莫属Django,但是Django的请求处理过程都是同步的无法实现异步任务,若要实现异步任务 ...

  7. MyBatis3系列__01HelloWorld

    # MyBatis作为一个ORM框架,其重要程度不用过多介绍.下面开始一起学习吧:本博客的编程方法与MyBatis官方文档基本一致:## 1.创建一个数据库mybatis_learn以及对应的表tbl ...

  8. 前端性能优化 —— 添加Expires头

    简要:添加Expires头能有效的利用浏览器的缓存能力来改善页面的性能,能在后续的页面中有效避免很多不必要的Http请求,WEB服务器使用Expires头来告诉Web客户端它可以使用一个组件的当前副本 ...

  9. python学习:输出九九乘法表

    输出九九乘法表 代码: num1 = 1while num1 <= 9: num2 = 1 while num2 <= num1: print(str(num2)+"*" ...

  10. JS基础学习3

    1.控制语句 (1)if控制语句 if-else基本格式 if (表达式){ 语句1; ...... }else{ 语句2; ..... } 功能说明 如果表达式的值为true则执行语句1, 否则执行 ...