- promise
- async await
- 防抖,节流
- 柯里化
- 实现 new,call, apply, bind
- lazyman
- flatten 数组扁平化
- 公布订阅
- 斐波那契数列生成
- 谬误重传封装
promise
promise 实现
async await
function async(genF){function spawn(genF) {return new Promise(function(resolve, reject) {const gen = genF();
function step(nextF) {
let next;
try {next = nextF();
} catch(e) {return reject(e);
}
if(next.done) {return resolve(next.value);
}
Promise.resolve(next.value).then(function(v) {step(function() {return gen.next(v); });
}, function(e) {step(function() {return gen.throw(e); });
});
}
step(function() {return gen.next(undefined); });
});
}
return spawn(genF);
}
防抖,节流
防抖:特定工夫距离之内不触发时调用
节流:特定工夫距离之内调用一次
// 防抖 特定工夫距离内不触发时才执行
function debounce(func, duration){
let timer;
return function(){
const context = this;
const args = [...arguments];
if(timer){clearTimeout(timer);
timer = null;
}
timer = setTimeout(function(){func.apply(context, args);
}, duration);
}
};
// 节流 特定工夫距离内只产生一次
function throttle(func, duration){
let timer;
return function(){
const context = this;
const args = [...arguments];
if(timer){return;}
timer = setTimeout(function(){func.apply(context, args);
clearTimeout(timer);
timer = null;
}, duration);
}
}
柯里化
在计算机科学中,柯里化(英语:Currying),又译为卡瑞化或加里化,是把承受多个参数的函数变换成承受一个繁多参数(最后函数的第一个参数)的函数,并且返回承受余下的参数而且返回后果的新函数的技术。
在直觉上,柯里化宣称“如果你固定某些参数,你将失去承受余下参数的一个函数”。
说人话就是把承受多个参数的函数转为多个嵌套的单个参数的函数。咱们应用场景的职责链模式是柯里化的例子,每个函数只解决本人关怀的参数。
柯里化的益处:
- 参数复用:一些固定参数不必反复传,比方类型校验函数。
- 提早调用:bind 函数
- 提前返回:如对 DOM 事件封装等,自执行函数中提前返回一个函数。下次不必做反复判断了。
// 柯里化
function currying(fn){
// 函数的参数个数
const max = fn.length;
let arr = [];
const closure = function(...args){arr = arr.concat(args);
// 没调用完,返回函数
if(arr.length < max){return closure;}else{return fn(...arr);
}
};
return closure;
}
function add(x, y, z) {return x + y + z}
curriedAdd = currying(add)
console.log('柯里化', curriedAdd(1, 2)(3));
实现 new, call, apply, bind
// call
Function.prototype.callFunc = function callFunc(){const self = [...arguments][0];
const args = [...arguments].slice(1);
self.fn = this;
const res = self.fn(...args);
delete self.fn;
return res;
}
// apply
Function.prototype.applyFunc = function applyFunc(){const self = [...arguments][0];
const args = [...arguments][1];
self.fn = this;
const res = self.fn(...args);
delete self.fn;
return res;
}
// bind
Function.prototype.bind = function(){
let self = this;
let context = [...arguments][0];
let args = [...arguments].slice(1);
return function(){return self.apply(context, [...args, ...arguments])
}
};
var getVal = function(z, m){return this.val + this.y + z + m;}
console.log(getVal.callFunc({
val: 456,
y: 123
},4,5));
console.log(getVal.applyFunc({
val: 456,
y: 123
}, [4,5]))
// 实现 new
function Create(Con, arguments){const Con = [...arguments][0];
const args = [...arguments].slice(1);
// 创立一个新对象
const obj = {};
// 指定原型
obj.setPropertyOf(Con.prototype);
// 执行构造函数
const res = Con.call(obj, ...args);
// 返回对象
return typeof res === 'object' ? res : obj;
}
lazyman
flatten 数组扁平化
// 数组扁平化
function flatten(arr = []){if(!arr.length){return arr;}
let res = [];
arr.forEach((item, index) => {if(!Array.isArray(item)){res.push(item);
}else{res = res.concat(flatten(item));
}
});
return res;
}
公布订阅
[公布]
斐波那契数列生成
// 斐波那契数列
function fibonacci(n){const arr = [0 ,1];
let a = 0;
let b = 1;
while(arr.length < n){[a, b] = [b, a + b];
arr.push(b);
}
return arr;
}
console.log('斐波那契数列', fibonacci(8));
谬误重传封装
// 重传
function retry(promiseFn, times = 3, duration = 200){return new Promise((resolve, reject) => {const handler = () => {promiseFn().then(res => resolve(res)).catch(err => {
times--;
if(!times){reject(err);
}else{setTimeout(handler, duration);
}
});
};
handler();});
}
function fetchData() {return new Promise(function(resolve, reject) {setTimeout(function() {console.log('server unavailable')
reject('server unavailable');
}, 500);
});
}
retry(fetchData)
主动重试