- 主题:花了一天实现了一个协程库
https://github.com/hgoldfish/qtng-jsasync () => {
let msg = await event.wait();
output(msg);
let r = await qtng.http.get("/test-data.html");
if (r.isOk) {
output(r.data);
} else {
console.debug(r.error);
}
}
因为只是原型,所以 http get 这些支持不太好。目前只能简单 get/post. 不过基本的功能都有了。
简单示例代码:
https://github.com/hgoldfish/qtng-js/blob/main/app/main.js
具体实现代码只有一个文件,并且没有依赖,但要求 js 支持 Map, async/await
https://github.com/hgoldfish/qtng-js/blob/main/app/qtng.js
--
FROM 110.85.22.*
别的先不说, 引入Semaphore, 是为了解决啥问题?
【 在 hgoldfish (老鱼) 的大作中提到: 】
:
https://github.com/hgoldfish/qtng-js: async () => {
: let msg = await event.wait();
: ...................
--
FROM 101.85.232.*
为了实现 Lock.
协程间通信很偶尔的情况会用到 Lock, Semaphore 和 Condition. 虽然很偶尔,但缺少这些同步机制的协程库都是不完整的。
其实 Lock 就是 jquery 的 Deferred,或者说 Promise,现在你也经常在用的吧。但协程库不能直接用 Deferred/Promise,因为协程 release 一个 Lock 之后,一般要等回事件循环以后才能跳到另外一个协程。所以要特别地提供一个 Lock. Lock 和 Semaphore 的实现方法一样,所以先实现一个 Semaphore.
Event 就是带值的 Lock, 如果无锁定,wait() 就直接返回值。否则加锁等待。set() 设置值并释放锁。上面那个帖子的实现其实不太对,github 上面的是针对协程的实现比较难懂。我这里换个写法给你看你就明白了:
class Event {
constructor() {
this.value = undefined;
this.deferred = new Deferred();
}
async wait() {
if (this.deferred) {
return await this.deferred.promise();
} else {
return this.value;
}
}
set(value) {
this.deferred = null;
this.value = value;
}
clear() {
this.deferred = new Deferred();
}
}
很简单对吧,也可以理解成只有一个槽的队列。大约再三十行代码就扩展成真正的 Queue 了。
【 在 pangwa (学门手艺,混口饭吃.) 的大作中提到: 】
: 别的先不说, 引入Semaphore, 是为了解决啥问题?
--
FROM 112.47.122.*
搞了半天你真的是在模拟generator啊?不说实现, 你确定它会更好用? ……
说实话我感觉你对js的一些库缺少了解,比如saga,rxjs,tj/co……
【 在 hgoldfish 的大作中提到: 】
:
: 为了实现 Lock.
:
: 协程间通信很偶尔的情况会用到 Lock, Semaphore 和 Condition. 虽然很偶尔,但缺少这些同步机制的协程库都是不完整的。
:
: 其实 Lock 就是 jquery 的 Deferred,或者说 Promise,现在你也经常在用
: ..................
发自「今日水木 on iPhone X」
--
FROM 114.85.182.*
Event 和 Promise 的使用场景是一样的。我举个例子。
比如你有两个模块,第一个模块负责登录,第二个模块需要登录以后才能用。两个模块都是框架调用的,你自己没法控制它们的顺序。这时候,你一般会设置一个:
let loginEvent = new Promise(...);
第二个模块要加载数据之前先等待登录事件:
loginEvent.then(...);
这时候 Event 跟 Promise 是完全一样的。相互可以代替:
let loginEvent = new Event();
await loginEvent.wait();
Event 和 Promise 使用上唯一不同的地方可能是 Event 可以被 clear(). 我实现 Event 主要是 Promise 不能被直接用于协程。作为对比,协程版本的 Event 的 Promise.all() 和 Promise.any() 这样写:
class Event {
static async all(events) {
for (let event of events)
if (!(await event.wait())) return false;
return true;
}
static async any(events) {
for (let event of events)
if (await event.wait()) return true;
return false;
}
}
总之,用了协程以后,一切回归到传统的 javascript 过程式编程,不再需要回调函数。
【 在 pangwa (学门手艺,混口饭吃.) 的大作中提到: 】
: 别的先不说, 引入Semaphore, 是为了解决啥问题?
--
FROM 112.47.122.*
感觉你太扣细节了。。Semaphore/Lock/Event 这些都是工具类,而且还是偶尔才用得上的工具类。我写在里面只是为了丰富工具库的内容。你关心那些有什么用啊。
你要讨论也讨论点核心啊。比如我那个 Coroutine 类可以说是整个工具库的核心。有了 Coroutine 和 CoroutineGroup 管理协程,给协程包个容器,才能实现我之前所说的 kill() 协程。
模拟 generator,你是不是在搞笑。我用的是 js 自带的 async/await 语法啊。。如果你不懂 async/await,建议你去看看相关的文章。为什么 js 要引入这个语法,而不是用 generator —— 我上面已经演示了 coroutine 可以实现 generator,但 generator 却未必能实现 coroutine,这是 js 引入 async/await 语法的原因。
你说的那些程序库,都是回调又回调。跟我压根不是一个路数。
【 在 pangwa (学门手艺,混口饭吃.) 的大作中提到: 】
: 搞了半天你真的是在模拟generator啊?不说实现, 你确定它会更好用? ……
: 说实话我感觉你对js的一些库缺少了解,比如saga,rxjs,tj/co……
: 发自「今日水木 on iPhone X」
: ...................
--
修改:hgoldfish FROM 112.47.122.*
FROM 112.47.122.*
仔细看看saga ……
【 在 hgoldfish 的大作中提到: 】
:
: 感觉你太扣细节了。。Semaphore/Lock/Event 这些都是工具类,而且还是偶尔才用得上的工具类。我写在里面只是为了丰富工具库的内容。你关心那些有什么用啊。
:
: 你要讨论也讨论点核心啊。比如我那个 Coroutine 类可以说是整个工具库的核心。有了 Coroutine
: ..................
发自「今日水木 on iPhone X」
--
FROM 114.85.182.*
如果你问。。新的协程库会比 rxjs 强吗?没有的,亲。
其实我觉得 rxjs/loaddash/vue/react 这一票,也没比 jquery 强多少。大多数功能,jquery 都能做,只是写起来很怪异。
我前面已经说了 Lock 和 Deferred/Promise 等价。所以 coroutine 和 promise,其实只是编程范式的区别而已。没有功能的差别。
【 在 pangwa (学门手艺,混口饭吃.) 的大作中提到: 】
: 搞了半天你真的是在模拟generator啊?不说实现, 你确定它会更好用? ……
: 说实话我感觉你对js的一些库缺少了解,比如saga,rxjs,tj/co……
: 发自「今日水木 on iPhone X」
: ...................
--
FROM 110.85.22.*
我前面不说了吗?? generator 和 coroutine 的区别。
你就当做一个 async/await 版本的 saga 就行了。
【 在 pangwa (学门手艺,混口饭吃.) 的大作中提到: 】
: 仔细看看saga ……
: 发自「今日水木 on iPhone X」
--
修改:hgoldfish FROM 110.85.22.*
FROM 110.85.22.*
你看 你说讨厌回调, saga就完全没有回调,至于你举的登录的例子,基于saga可以写的比你这个好看多了,无非是你觉得协程好就一定要在js中实现一个蹩脚的协程,实际上这个世界有其他更好的模式解决这些问题啊……
【 在 hgoldfish 的大作中提到: 】
:
: 如果你问。。新的协程库会比 rxjs 强吗?没有的,亲。
:
: 其实我觉得 rxjs/loaddash/vue/react 这一票,也没比 jquery 强多少。大多数功能,jquery 都能做,只是写起来很怪异。
:
: 我前面已经说了 Lock 和 Deferred/Pr
: ..................
发自「今日水木 on iPhone X」
--
FROM 114.85.182.*