node.js里由于回调函数层层嵌套,使用变量似乎是一件要很谨慎的事?

2012-12-04 11:52:03 +08:00
 robhsiao
初次用expressjs写了点小东西,窃以为变量作用域名是node.js(或者应该是javascript) ugly的一个地方。

基本每一个模块需要占用一个全局变量,而且由于回调函数里可能需要使用父级函数的局部变量,所以回调函数嵌套几层之后,感觉使用每一个变量要非常谨慎,每一个变量都是一个炸弹。


请问大家是如何规避这个问题?依靠命名规范?或者是我用法是不正确?
13334 次点击
所在节点    Node.js
26 条回复
jackyz
2012-12-05 15:38:07 +08:00
@linlinqi

谢谢重构,两个感觉不太适应的地方:

1. 10 行变成 23 行 ,没感觉在哪里变得更清晰了呢?
2. 从 node 的 callback(e,r) 风格转变为 resolve -> done reject -> fail 风格。

另外,如果再加一层回调呢,会变成什么样子?在实际应用中有个 5,6 层的回调不稀奇呀。

那个层次还需要再包装 resolve 和 reject 还是可以“重用” promise 又或者怎样?各个层次的异常如果要有不同的处理代码,要怎么表达呢?是:
fun1().done().fail().fun2().done().fail()
还是:
fun().done( fun2().done().fail() ).fail()
又或者还是怎样?

之前的尝试,进行到这里就退回去了(感觉没啥区别呀,而且还要分别包装 e 和 r ),没准我是那个关节没相通?
luin
2012-12-05 15:59:35 +08:00
@jackyz 你觉得使用async如何呢?
http://gist.github.com/4213629
linlinqi
2012-12-05 17:33:24 +08:00
@jackyz 假设redis这个对象已经是基于Deferred模式封装良好的话,那么写的好看一些会是这样

http://gist.github.com/4212565.js?file=ahhhh.js

这样的行数是不是满足了?
jackyz
2012-12-05 19:20:05 +08:00
嵌套层次太多确实难看。要追求漂亮,但不能以失去灵活性为代价。

@luin 论坛氛围不错,我改写了例子,希望能把问题引向更深入。
主要的改写是引入了需要传递更多因素的情况,来表达这种灵活性在使用 control flow module 之后的丧失。

http://gist.github.com/4214679.js

引入之后,感觉有两个问题。

传参自由度的问题:

第 6 行分别引用了两个外层里定义的 id 和 val 。对应在 async 写法的第 24 行,是不 work 的。要解决这个问题,需要显式地向外用 callback 传递或者引入一个 params object 来解决问题。需要传递的参数更多的话,可能更麻烦。

async 的思路是通过 callback 的参数传递给下一个 function 。各个 function 的变量作用域是并列的,也就是说,嵌套层次的扁平是以引用外层变量的能力作为代价的。

错误处理自由度的问题:

上述每一个错误都给了一个不同的错误处理,之前的例子是全都用 next(e) 来处理,所以,体现不出这种约束来。在 async 的版本里,所有的错误都汇集到 27 行来处理,要如何区分这许多种错误呢?

我也有用 async ,主要是用它抽象数据结构的相关方法,比如 map 之类,但 control flow 的因为上述的问题,就暂时还没有用。

@linlinqi 这是否意味着需要在 callback(e,r) 的 node.js 标准风格和 deferred 风格之间做适配呢?这个适配,在 node 没有推出标准的 deferred 风格之前,似乎是没有动力去完成的。

还是那句话,要追求漂亮,但不能以失去灵活性为代价。我知道这可能有些不切实际,必然要 trade off 什么的。不过,思考一下倒也有益。
jackyz
2012-12-07 17:10:26 +08:00
这个问题踢到铁板讨论不下去了吗?
robhsiao
2012-12-07 17:49:11 +08:00
sorry, 楼主读书不多,只能围观 :(
各位请继续...

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/54041

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX