Created
February 22, 2023 08:59
-
-
Save eczn/e224416af635d0e2b4fd65ee06f930b9 to your computer and use it in GitHub Desktop.
异步并发控制,曾经某郭姓男子问的【存档备份】
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
type Task<T> = () => (T | Promise<T>); | |
type UnLock = () => void; | |
class ProcessLock { | |
private count = 0; | |
private queue: UnLock[] = []; | |
constructor(public capacity: number) {} | |
request = async (): Promise<UnLock> => { | |
if (this.count >= this.capacity) { | |
await new Promise<void>((resolve) => { | |
this.queue.push(resolve); | |
}); | |
return this.request(); | |
} | |
this.count = this.count + 1; | |
return () => { | |
this.count = this.count - 1; | |
this.queue.shift()?.(); // 这里不能是 pop 哦, 要执行最早进来的任务 | |
} | |
} | |
} | |
/** | |
* 异步并发控制器 | |
*/ | |
export function createAsyncWorker(capacity: number): <T>(task: Task<T>) => Promise<T> { | |
const plock = new ProcessLock(capacity); | |
// show me your code | |
return async function<T>(task: Task<T>): Promise<T> { | |
const release = await plock.request(); // 申请一下资源, 没有的话就等 | |
try { | |
const result = await task(); // 跑任务 | |
release(); // 不要忘记释放哦 | |
return result; // 返回结果 | |
} catch (error) { | |
release(); // 出错了也要释放哦 | |
throw error; | |
} | |
}; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment