65.9K
CodeProject 正在变化。 阅读更多。
Home

在 MongoDB 中向集合添加新文档

emptyStarIconemptyStarIconemptyStarIconemptyStarIconemptyStarIcon

0/5 (0投票)

2015年4月12日

CPOL

2分钟阅读

viewsIcon

11537

如何更高效地向集合添加新文档

引言

本技巧涵盖了将数据移动到数据库的基本知识,包括以下内容:

1) 插入

2) 批量插入

对于第一部分

要将文档插入到集合中,我们可以使用以下命令:

> db.tasks.insert({"user" : "Coldsky", "finished" :  1, "unfinished" : 10})

这将为文档添加一个额外的 "_id",然后将其存储在 mongodb 中。 

请注意,mongodb 将确保 "_id" 是唯一的,并且也会被索引,这有助于提高查询性能。

我想大多数人都想知道插入方法的性能,所以让我们将一百万个文档插入到一个集合中,并注意它所消耗的时间。我已经创建了一个函数来执行此操作,请参见下文:

> var insertT = function() {
    var start = (new Date()).getTime();
    for (var i=0; i< 1000000; i++) {
        db.task1.insert({"user" : "Coldsky", "finished" : i, "unfinished" : 1000000 - i})
    }
    var end  = (new Date()).getTime();
    var diff = end -start;
    print("Insert 1M documents took " + diff + "ms" )
    }
> insertT()
Insert 1M documents took 409438ms

我们可以看到插入速率为每秒 2500 个文档。我们发现我们无法容忍这种低性能。幸运的是,批量插入可以在这种情况下提供帮助,让我们在第二部分中看看。

对于第二部分

什么是批量插入?批量插入允许您将文档数组传递给集合,它减少了与 mongodb 服务器交互时的 io 次数,因此与普通插入相比,性能得到了很大的提高。

我还需要一个函数来进行性能测试,请参见下文:

> var InsertTime = function() { 
    var start = (new Date()).getTime();
    for (var i=0; i< 10; i++) { 
        var tasks = new Array(); 
        for (var j=0; j< 100000;j++) { 
            tasks[j] = {"user" : "Coldsky", "finished" : i*100000 +j, "unfinished": 1000000 - i*100000 -j}         
        } 
        db.task2.insert(tasks); 
    } 
    var end = (new Date()).getTime(); 
    var diff = end - start; 
    print("Insert 1M documents took " + diff + "ms"); 
  }

> InsertTime()
Insert 1M documents took 56691ms

我们可以看到,我们使用了 10 个批量插入将一百万个文档插入到一个集合中,插入速率为每秒 17636 个文档,性能是普通插入的 7 倍。

因此,当我们进行大规模插入时,我们应该首先考虑批量插入,并且我想提供一种通用的批量插入方法:

> var InsertTime = function() { 
    var start = (new Date()).getTime();
    for (var i=0; i<(n-n%m)/m; i++) { 
        var tasks = new Array(); 
        for (var j=0; j<m;j++) { 
            tasks[j] = {"user" : "Coldsky", "finished" : i*100000 +j, "unfinished": 1000000 - i*100000 -j}         
        } 
        db.taskMgr.insert(tasks); 
    }
    
    var tasks = new Array();
    for (var i=n-n%m; i<n; i++) {
        tasks[i - (n - n%m)] = {"user" : "Coldsky", "finished" : i, "unfinished" : n-i}
    }
    db.taskMgr.insert(tasks);
    var end = (new Date()).getTime(); 
    var diff = end - start; 
    print("Insert 1M documents took " + diff + "ms"); 
​  }

其中 n 是您要插入到数据库中的总文档数,而 m 是单个批量插入中的文档数。

还需要注意的是,“m”个文档的大小不应超过 48M,否则 mongodb 驱动程序会将批量插入拆分为多个 48M 的批量插入。

要检查“m”个文档的大小是否超过 48M,我们可以使用 Object.bsonsize() 方法,只需将包含“m”个文档的数组作为参数即可。 

本技巧到此结束。感谢您的阅读,如果您有任何问题,请随时与我联系。

© . All rights reserved.