经典的单例模式
代码语言:javascript复制function proxy(func) {
let instance
let handler = {
construct(target, args) {
if (!instance) {
instance = Reflect.construct(func, args)
}
return instance
}
}
return new Proxy(func, handler)
}
instanceof
代码语言:javascript复制const selfInstance = function (left, right) {
let proto = Object.getPrototypeOf(left)
if (proto == null) return false
if (proto === right.prototype) {
return true
}
proto = Object.getPrototypeOf(proto)
}
promise的实现
代码语言:javascript复制class Promise {
constructor (fn) {
// 三个状态
this.state = 'pending'
this.value = undefined
this.reason = undefined
let resolve = value => {
if (this.state === 'pending') {
this.state = 'fulfilled'
this.value = value
}
}
let reject = value => {
if (this.state === 'pending') {
this.state = 'rejected'
this.reason = value
}
}
// 自动执行函数
try {
fn(resolve, reject)
} catch (e) {
reject(e)
}
}
// then
then(onFulfilled, onRejected) {
switch (this.state) {
case 'fulfilled':
onFulfilled()
break
case 'rejected':
onRejected()
break
default:
}
}
}
防抖函数
代码语言:javascript复制// 思路:在规定时间内未触发第二次,则执行
function debounce (fn, delay) {
// 利用闭包保存定时器
let timer = null
return function () {
let context = this
let arg = arguments
// 在规定时间内再次触发会先清除定时器后再重设定时器
clearTimeout(timer)
timer = setTimeout(function () {
fn.apply(context, arg)
}, delay)
}
}
function fn () {
console.log('防抖')
}
addEventListener('scroll', debounce(fn, 1000))
复制代码
节流函数
代码语言:javascript复制function throttle (fn, delay) {
// 利用闭包保存时间
let prev = Date.now()
return function () {
let context = this
let arg = arguments
let now = Date.now()
if (now - prev >= delay) {
fn.apply(context, arg)
prev = Date.now()
}
}
}
function fn () {
console.log('节流')
}
addEventListener('scroll', throttle(fn, 1000))
复制代码
实现一个call函数
// 思路:将要改变this指向的方法挂到目标this上执行并返回
代码语言:javascript复制Function.prototype.call = function (context) {
if (typeof this !== 'function') {
throw new TypeError('not funciton')
}
context = context || window
context.fn = this
let arg = [...arguments].slice(1)
let result = context.fn(...arg)
delete context.fn
return result
}
实现一个apply函数
// 思路:将要改变this指向的方法挂到目标this上执行并返回
代码语言:javascript复制Function.prototype.myapply = function (context) {
if (typeof this !== 'function') {
throw new TypeError('not funciton')
}
context = context || window
context.fn = this
let result
if (arguments[1]) {
result = context.fn(...arguments[1])
} else {
result = context.fn()
}
delete context.fn
return result
}
实现一个bind函数
// 思路:类似call,但返回的是函数
代码语言:javascript复制Function.prototype.mybind = function (context) {
if (typeof this !== 'function') {
throw new TypeError('Error')
}
let _this = this
let arg = [...arguments].slice(1)
return function F() {
// 处理函数使用new的情况
if (this instanceof F) {
return new _this(...arg, ...arguments)
} else {
return _this.apply(context, arg.concat(...arguments))
}
}
}
复制代码