We read every piece of feedback, and take your input very seriously.
To see all available qualifiers, see our documentation.
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
函数调用 n 秒后才会执行,如果函数在 n 秒内被调用的话则函数不执行,重新计算执行时间,这里的原理是利用了一个闭包,每当有事件被监听就清除闭包中timer,重新赋值
timer
// debounce function debounce(method, delay) { var timer = null; return function () { var context = this, args = arguments; clearTimeout(timer); timer = setTimeout(function () { method.apply(context, args); }, delay); } }
比如resize()一瞬间调用了很多次,只会延迟触发最后一次调用,再比如用户在短时间触发了很多次输入动作oninput,就会延迟只触发最后一次,我们可以把它用在scroll、resize和input这些事件监听上,减少不必要的性能开销,还可以在下列事件下做去抖处理
resize()
oninput
scroll、resize和input
window
resize、scroll
mousemove
mousedown、keydown
keyup
function resizeHandler() { console.log(this); } window.onresize = debounce(resizeHandler, 500); function inputHandler() { console.log(this); } document.getElementById("input").oninput = debounce(inputHandler, 500);
更进一步,我们不希望非要等到事件停止触发后才执行,我希望立刻执行函数,然后等到停止触发 n 秒后,才可以重新触发执行 这里增加一个 immediate 参数来设置是否要立即执行
function debounce(func, delay, immediate) { var timer = null; return function () { var context = this; var args = arguments; if (timer) clearTimeout(timer); if (immediate) { //根据距离上次触发操作的时间是否到达delay来决定是否要现在执行函数 var doNow = !timer; //每一次都重新设置timer,就是要保证每一次执行的至少delay秒后才可以执行 timer = setTimeout(function () { timer = null; }, delay); //立即执行 if (doNow) { func.apply(context, args); } } else { timer = setTimeout(function () { func.apply(context, args); }, delay); } } }
函数预先设定一个执行周期,当调用动作的时刻大于等于执行周期则执行该动作,然后进入下一个新周期
// throttle function throttle(method, duration) { var begin = new Date(); return function () { var context = this, args = arguments, current = new Date(); if (current - begin >= duration) { method.apply(context, args); begin = current; } } }
vscode/extensions/git/src/decorators.ts
import { done } from './util'; function decorate(decorator: (fn: Function, key: string) => Function): Function { return (_target: any, key: string, descriptor: any) => { let fnKey: string | null = null; let fn: Function | null = null; if (typeof descriptor.value === 'function') { fnKey = 'value'; fn = descriptor.value; } else if (typeof descriptor.get === 'function') { fnKey = 'get'; fn = descriptor.get; } if (!fn || !fnKey) { throw new Error('not supported'); } descriptor[fnKey] = decorator(fn, key); }; } function _memoize(fn: Function, key: string): Function { const memoizeKey = `$memoize$${key}`; return function (this: any, ...args: any[]) { if (!this.hasOwnProperty(memoizeKey)) { Object.defineProperty(this, memoizeKey, { configurable: false, enumerable: false, writable: false, value: fn.apply(this, args) }); } return this[memoizeKey]; }; } export const memoize = decorate(_memoize); function _throttle<T>(fn: Function, key: string): Function { const currentKey = `$throttle$current$${key}`; const nextKey = `$throttle$next$${key}`; const trigger = function (this: any, ...args: any[]) { if (this[nextKey]) { return this[nextKey]; } if (this[currentKey]) { this[nextKey] = done(this[currentKey]).then(() => { this[nextKey] = undefined; return trigger.apply(this, args); }); return this[nextKey]; } this[currentKey] = fn.apply(this, args) as Promise<T>; const clear = () => this[currentKey] = undefined; done(this[currentKey]).then(clear, clear); return this[currentKey]; }; return trigger; } export const throttle = decorate(_throttle); function _sequentialize(fn: Function, key: string): Function { const currentKey = `__$sequence$${key}`; return function (this: any, ...args: any[]) { const currentPromise = this[currentKey] as Promise<any> || Promise.resolve(null); const run = async () => await fn.apply(this, args); this[currentKey] = currentPromise.then(run, run); return this[currentKey]; }; } export const sequentialize = decorate(_sequentialize); export function debounce(delay: number): Function { return decorate((fn, key) => { const timerKey = `$debounce$${key}`; return function (this: any, ...args: any[]) { clearTimeout(this[timerKey]); this[timerKey] = setTimeout(() => fn.apply(this, args), delay); }; }); }
The text was updated successfully, but these errors were encountered:
No branches or pull requests
去抖
函数调用 n 秒后才会执行,如果函数在 n 秒内被调用的话则函数不执行,重新计算执行时间,这里的原理是利用了一个闭包,每当有事件被监听就清除闭包中
timer
,重新赋值比如
resize()
一瞬间调用了很多次,只会延迟触发最后一次调用,再比如用户在短时间触发了很多次输入动作oninput
,就会延迟只触发最后一次,我们可以把它用在scroll、resize和input
这些事件监听上,减少不必要的性能开销,还可以在下列事件下做去抖处理window
对象的resize、scroll
事件mousemove
事件mousedown、keydown
事件keyup
事件更进一步,我们不希望非要等到事件停止触发后才执行,我希望立刻执行函数,然后等到停止触发 n 秒后,才可以重新触发执行
这里增加一个 immediate 参数来设置是否要立即执行
节流
函数预先设定一个执行周期,当调用动作的时刻大于等于执行周期则执行该动作,然后进入下一个新周期
Vscode 的写法
vscode/extensions/git/src/decorators.ts
参考文档
The text was updated successfully, but these errors were encountered: