node.js将两个数组与对象

时间:2015-11-24 21:11:27

标签: javascript arrays node.js mongodb

我需要从我的mongo db中删除所有文件,这些文件在带有对象的新数组中不存在。 所以我有像以下对象的数组:

var items = [
{product_id:15, pr_name: 'a', description : 'desc'},
{product_id:44, pr_name: 'b', description : 'desc2'}
{product_id:32, pr_name: 'c', description : 'desc3'}];

我有一个带有db值的数组,我可以通过调用 Model.find({})获得。 所以现在我直接做到这一点。方式:

async.each(products, function (dbProduct, callback) { //cycle for products removing
    var equals = false;

    async.each(items, function(product, callback){
        if (dbProduct.product_id === product.product_id){
            product.description = dbProduct.description;// I need to save desc from db product to new product
            equals = true;
        }
        callback();
    });

    if (!equals) {
        log.warn("REMOVE PRODUCT " + dbProduct.product_id);
        Product.remove({ _id: dbProduct._id }, function (err) {
            if (err) return updateDBCallback(err);
            callback();
        });
    }

});

但它阻止了整个应用程序并且非常慢,因为我的 项目 数组和数据库中的值大约为5000。因此它的周期数非常庞大。 也许可以有更快的方式?

UPDATE1 使用以下代码,来自 TbWill4321 回答:

var removeIds = [];

// cycle for products removing
async.each(products, function (dbProduct, callback) {
    for ( var i = 0; i < items.length; i++ ) {
        if (dbProduct.product_id === product.product_id) {
            // I need to save desc from db product to new product
            product.description = dbProduct.description;
            // Return early for performance
            return callback();
        }
    }

    // Mark product to remove.
    removeIds.push( dbProduct._id );
    log.warn("REMOVE PRODUCT " + dbProduct.product_id);
    return callback();
}, function() {
    Product.remove({ _id: { $in: removeIds } }, function (err) {
        if (err) return updateDBCallback(err);
        // Continue Here.
        // TODO
    });
});

它需要大约11秒(阻止整个网络应用程序)并为我带来12 362 878个周期。 那么也许有人可以给我一些建议?

2 个答案:

答案 0 :(得分:1)

在您可能遇到的许多问题中,您可能希望从更改此位开始:

Product.remove({ _id: dbProduct._id }, function (err) {
        if (err) return updateDBCallback(err);
        callback();
});

.each()电话中,您将为要删除的每个元素拨打一次数据库。最好将所有ID存储在 one 数组中,然后进行单个查询以删除所有具有该数组中的_id的元素。喜欢这个

Product.remove({ _id: {$in: myArrayWithIds} }, function (err) {
        if (err) return updateDBCallback(err);
        callback();
});

另一方面,由于async将同步执行,因此node.js提供了setImmediate()(docs here),它将在事件循环中执行该函数。所以基本上你可以&#34;暂停&#34;执行新元素并提供任何传入请求以模拟&#34;非阻塞&#34;处理

答案 1 :(得分:1)

异步库以异步方式执行同步代码。

对于JavaScript来说5000个项目并不是一个庞大的数字,因为我已经在500万+点的大数据集上工作,并且不需要很长时间。您可以通过以下结构获得更好的性能:

var removeIds = [];

// cycle for products removing
async.each(products, function (dbProduct, callback) {
    for ( var i = 0; i < items.length; i++ ) {
        if (dbProduct.product_id === product.product_id) {
            // I need to save desc from db product to new product
            product.description = dbProduct.description;
            // Return early for performance
            return callback();
        }
    }

    // Mark product to remove.
    removeIds.push( dbProduct._id );
    log.warn("REMOVE PRODUCT " + dbProduct.product_id);
    return callback();
}, function() {
    Product.remove({ _id: { $in: removeIds } }, function (err) {
        if (err) return updateDBCallback(err);
        // Continue Here.
        // TODO
    });
});