事情是这样的,产品的同事希望在一个用户列表中,按照不同的标准选取几类用户(假设有A, Bl两种用户),然后同时呈现。但是有些用户可能同时满足2个标准,比如某个用户既符合A标准,也符合B标准,这样返回的结果如果不加限定,就会出现同一个用户出现多次的情况。
现在我是这么考虑的,先去找A类的用户,查找结束后,把A类用户的_id传递给第二个函数,第二个函数在查找B类用户时候,把第所有A类用户的_id都剔除掉。程序结构大概是这样:
var exclude = [];
async.series( [
function( callback ) {
db.collection('users').find( { /*category A的条件*/} ).toArray( function( err, users ) {
users.forEach( function( user ) {
exclude.push( user._id );
} );
callback( null, users );
} )
},
function( callback ) {
db.collection('users').find( { /*category B的条件*/ _id : { $not : { $in : exclude } }/*限定不包含category A的用户*/ } ).toArray( function( err, users ) {
callback( null, users );
} )
}
], function( err, result ) {
var users_A = result[0];
var users_B = result[1];
// Handle category A and B...
} )
为了保证不重复,需要A执行完后在执行B。顺序执行,响应时间太长。如果改成并发执行,那么每个函数去查找用户时,都要包含{$not : { $in : exclude } }条件。关键是是否会出现这样一种情况: 第一个函数先执行回调,然后向exclude写入id,还没有写完时,第二个函数执行回调了,但是exclude还是空的,那么exclude的限定在第二个函数里其实就没有作用了。
小弟表达能力较差,说的不清楚的地方,还请大家指出,期待各路高手给点儿意见啊,跪谢先 m( _ _ ) m