2011-06-14 44 views
16

从性能的角度看,嵌入效果更好: “如果性能是一个问题,嵌入”。 (http://www.mongodb.org/display/DOCS/Schema+Design)和大多数指南总是说包含应嵌入。从性能角度来看,嵌入MongoDB与参考相比

但是我不确定是这种情况。假设我们有两个对象:Blog和Post。博客包含帖子。

现在正在嵌入博客将有以下问题的所有帖子:

  1. 寻呼。由于无法过滤嵌入对象,因此我们将始终获取所有帖子,并需要在应用程序中将其过滤掉。
  2. Filtering。与之前一样,当在帖子内搜索单词时,将无法从MongoDB过滤嵌入的收藏集。
  3. 插入。我认为插入到集合比插入到嵌入对象更快。它是否正确?这是写在任何地方?
  4. 更新。和以前一样,小文档(Post)内嵌入更新字段可能会更快,然后内联更新Blog的大文档内的帖子。它是否正确?

考虑到上述所有情况,我会选择在引用Blog的单独集合中发布帖子。这是正确的结论吗?

(注:请不要因素文件大小限制在响应中,假设每个博客都会有最多1000个)

回答

12

1.Paging可能与$slice操作:

db.blogs.find({}, {posts:{$slice: [10, 10]}}) // skip 10, limit 10 

2.Filtering也可能的:

db.blogs.find({"posts.title":"Mongodb!"}, {posts:{$slice: 1}}) //take one post 

3,4。一般来说,我猜你是在谈论小的性能差异。这不是火箭科学,它最多只有1000个博客。

你说:

Is this the correct conclusion? 

没有,如果你关心性能(一般来说,如果系统将是小,你可以用单独的文件去)。

我已经做了关于3,4-小的性能测试,这里是结果:

----------------------------------------------------------------- 
| Count/Time | Inserting posts | Adding to nested collection | 
-------------|--------------------------------------------------    
| 1  | 1 ms    | 28 ms      | 
| 1000  | 81 ms   | 590 ms      | 
| 10000 | 759 ms   | 2723 ms     | 
--------------------------------------------------------------- 
+0

谢谢你的详细解答。 – mbdev 2011-06-15 06:33:40

+0

@mbdev:不客气。 – 2011-06-15 07:14:46

+0

你确定#2是否有一个帖子与标题相匹配?我想它会返回包含“Mongodb!”帖子的博客标题。然后切片只会过滤第一篇文章。所以你会得到不正确的帖子 – mbdev 2011-06-16 15:02:23

1
  1. 可以嵌入元素
  2. “$切片”分页
  3. 您可以用“field1.field2”进行搜索:/ aRegex/ with aRegex是您搜索的词。但照顾性能。

约3.和4.我没有证据数据。

BTW 2集合可以更容易编码/使用/管理。你可以简单的每个 '博客' 文件中注册blogId并添加“blogId”: “1234ABCD”在所有查询

2

至于3 & 4,如果你插入一个嵌套的文件,它基本上是一个更新。

这对于您的性能可能会非常糟糕,因为插入通常会附加到数据的结尾,而且工作正常且快速。另一方面,更新可能会更棘手。

如果你的更新没有改变文档的大小(意味着你有一个键\值对,只是将值更改为占用相同空间量的新值),那么你会没事的,但是当您开始修改文档并添加新数据,则会出现问题。

问题是,虽然MongoDB为每个文档分配的空间比它需要的多,但可能还不够。如果您插入的文档大小为1K,则MongoDB可能会为文档分配1.5k,以确保对文档的微小更改有足够的空间进行扩展。如果您使用的分配空间不止一个,MongoDB必须获取整个文档并在数据的尾部重新写入。

在获取和重写数据时会有明显的性能影响,这些数据会被这种操作的频率放大。更糟糕的是,当发生这种情况时,最终会在数据文件中留下空洞或未使用的空间。

这最终被复制到内存中,这意味着您最终可能会使用2GB的RAM来存储您的数据集,而实际上数据本身只占用1.5GB,因为有0.5GB的口袋。这种碎片可以通过插入而不是更新来避免。它也可以通过修复数据库来修复。

在下一个版本的MongoDB中将会有一个在线压缩功能。

+0

你认为数字会比安德鲁的数字更糟? – mbdev 2011-06-16 12:50:28

+0

不可能说 - 我取决于您的数据结构和文档大小以及嵌入文档的100%。一旦尝试插入大于分配的可用空间的文档,您将看到写入时的性能下降。我认为用相对较小的数据集进行小型测试很难证明这一点。 – 2011-06-16 14:19:49