@@ -129,8 +129,11 @@ var outputPromise = getInputPromise().then(function(fulfiled){
129
129
现在outputPromise就变成了受function(fulfiled)或者function(rejected)控制状态的promise了。怎么理解这句话呢?
130
130
131
131
* 当function(fulfiled)或者function(rejected)返回一个值,比如一个字符串,数组,对象等等,那么outputPromise的状态就会变成fulfiled。
132
+
132
133
在下面这个例子中,我们可以看到,当我们把inputPromise的状态通过defer.resovle()变成fulfiled时,控制台输出fulfiled.
134
+
133
135
当我们把inputPromise的状态通过defer.reject()变成rejected,控制台输出rejected
136
+
134
137
``` js
135
138
/**
136
139
* 通过defer获得promise
@@ -176,6 +179,128 @@ var outputPromise = getInputPromise().then(function(fulfiled){
176
179
```
177
180
* 当function(fulfiled)或者function(rejected)抛出异常时,那么outputPromise的状态就会变成rejected
178
181
182
+ ``` JS
183
+ var Q = require (' q' );
184
+ var fs = require (' fs' );
185
+ var defer = Q .defer ();
186
+
187
+ /**
188
+ * 通过defer获得promise
189
+ * @private
190
+ */
191
+ function getInputPromise () {
192
+ return defer .promise ;
193
+ }
194
+
195
+ /**
196
+ * 当inputPromise状态由未完成变成fulfil时,调用function(fulfiled)
197
+ * 当inputPromise状态由未完成变成rejected时,调用function(rejected)
198
+ * 将then返回的promise赋给outputPromise
199
+ * function(fulfiled) 和 function(rejected) 通过抛出异常将outputPromise的状态由
200
+ * 未完成改变为reject
201
+ * @private
202
+ */
203
+ var outputPromise = getInputPromise ().then (function (fulfiled ){
204
+ throw new Error (' fulfiled' );
205
+ },function (rejected ){
206
+ throw new Error (' rejected' );
207
+ });
208
+
209
+ /**
210
+ * 当outputPromise状态由未完成变成fulfil时,调用function(fulfiled),控制台打印'[Error:fulfiled]'。
211
+ * 当outputPromise状态由未完成变成rejected, 调用function(rejected), 控制台打印'[Error:rejected]'。
212
+ */
213
+ outputPromise .then (function (fulfiled ){
214
+ console .log (fulfiled);
215
+ },function (rejected ){
216
+ console .log (rejected);
217
+ });
218
+
219
+ /**
220
+ * 将inputPromise的状态由未完成变成rejected
221
+ */
222
+ defer .reject ();
223
+
224
+ /**
225
+ * 将inputPromise的状态由未完成变成fulfiled
226
+ */
227
+ // defer.resolve();
228
+ ```
229
+
230
+ * 当function(fulfiled)或者function(rejected)返回一个promise时,outputPromise就会成为这个新的promise.
231
+
232
+ 这样做有什么意义呢? 主要在于聚合结果(Q.all),管理延时,异常恢复等等
233
+
234
+ 比如说我们想要读取一个文件的内容,然后把这些内容打印出来。可能会写出这样的代码:
235
+
236
+ ``` js
237
+ // 错误的写法
238
+ var outputPromise = getInputPromise ().then (function (fulfiled ){
239
+ fs .readFile (' test.txt' ,' utf8' ,function (err ,data ){
240
+ return data;
241
+ });
242
+ },function (rejected ){
243
+ throw new Error (' rejected' );
244
+ });
245
+ ```
246
+
247
+ 然而由于异步IO的原因,这样写是不行的。需要下面的方式:
248
+
249
+ ``` js
250
+ var Q = require (' q' );
251
+ var fs = require (' fs' );
252
+ var defer = Q .defer ();
253
+
254
+ /**
255
+ * 通过defer获得promise
256
+ * @private
257
+ */
258
+ function getInputPromise () {
259
+ return defer .promise ;
260
+ }
261
+
262
+ /**
263
+ * 当inputPromise状态由未完成变成fulfil时,调用function(fulfiled)
264
+ * 当inputPromise状态由未完成变成rejected时,调用function(rejected)
265
+ * 将then返回的promise赋给outputPromise
266
+ * function(fulfiled)将新的promise赋给outputPromise
267
+ * 未完成改变为reject
268
+ * @private
269
+ */
270
+ var outputPromise = getInputPromise ().then (function (fulfiled ){
271
+ var myDefer = Q .defer ();
272
+ fs .readFile (' test.txt' ,' utf8' ,function (err ,data ){
273
+ if (! err && data) {
274
+ myDefer .resolve (data);
275
+ }
276
+ });
277
+ return myDefer .promise ;
278
+ },function (rejected ){
279
+ throw new Error (' rejected' );
280
+ });
281
+
282
+ /**
283
+ * 当outputPromise状态由未完成变成fulfil时,调用function(fulfiled),控制台打印'[Error:fulfiled]'。
284
+ * 当outputPromise状态由未完成变成rejected, 调用function(rejected), 控制台打印'[Error:rejected]'。
285
+ */
286
+ outputPromise .then (function (fulfiled ){
287
+ console .log (fulfiled);
288
+ },function (rejected ){
289
+ console .log (rejected);
290
+ });
291
+
292
+ /**
293
+ * 将inputPromise的状态由未完成变成rejected
294
+ */
295
+ // defer.reject();
296
+
297
+ /**
298
+ * 将inputPromise的状态由未完成变成fulfiled
299
+ */
300
+ defer .resolve ();
301
+ ```
302
+
303
+
179
304
这次我们要介绍的是 async 的 ` mapLimit(arr, limit, iterator, callback) ` 接口。另外,还有个常用的控制并发连接数的接口是 ` queue(worker, concurrency) ` ,大家可以去 https://github.com/caolan/async#queueworker-concurrency 看看说明。
180
305
181
306
这回我就不带大家爬网站了,我们来专注知识点:并发连接数控制。
0 commit comments