14

最近我正在探索 NoSQL 数据库。对于给定的问题,我需要关于如何以最优化和最有效的方式存储数据的建议。我现在的目标是 MongoDB。但是它应该与 CouchDB 相同。

假设我们有这 3 个模型:

Story:
 id
 title

User:
 id
 name

Vote:
  id
  story_id
  user_id

我希望能够向数据库询问这些问题:

  • 谁为这个故事投票?
  • 该用户投票支持什么?

我在使用关系数据库时正在做简单的连接。问题是,我应该如何存储这些对象的数据才能最有效。

例如,如果我将 Vote 对象存储为 Stories 的子集合,那么获取信息并不容易 - “用户投票支持的内容”。

4

5 回答 5

7

我建议将投票存储为_id每个用户的故事列表。这样,您只需查看列表即可找出用户投票支持的故事。要获得为故事投票的用户,您可以执行以下操作:

db.users.find({stories: story_id})

story_id_id问题的故事在哪里。如果您在字段上创建索引,那么stories这两个查询都会很快。

于 2009-11-29T16:18:33.623 回答
3
  • 不要担心您的查询是否有效,直到它开始变得重要
  • 根据下面的报价,你做错了

我一直在进行思维转换的方法是完全忘记数据库。在关系数据库世界中,您总是需要担心数据规范化和表结构。抛弃一切。只需布局您的网页。把它们都摆出来。现在看看他们。你已经有 2/3 了。如果您忘记了数据库大小很重要并且数据不应该重复超过 3/4 的概念,那么您甚至不必编写任何代码!让你的观点决定你的模型。您不必再像在关系世界中那样将您的对象变成二维的。您现在可以存储具有形状的对象。

如何在数据存储而不是数据库中思考

于 2010-01-09T02:44:27.660 回答
2

好的,你已经给出了一个标准化的数据模型,就像你在 SQL 设置中所做的那样。

据我了解,您不会在 MongoDB 中执行此操作。您可以存储引用,但在一般情况下出于性能原因您不这样做。

我绝不是 NoSQL 领域的专家,但你为什么不简单地按照你的需求,将投票给故事的用户(id)存储在故事集合中,以及用户拥有的故事(id)在用户收藏中投票?

于 2009-11-29T16:13:44.370 回答
1

在 CouchDB 中,这非常简单。一个视图发出:

function(doc) {
 if(doc.type == "vote") {
   emit(doc.story_id, doc.user_id);
 }
}

另一个视图发出:

function(doc) {
 if(doc.type == "vote") {
   emit(doc.user_id, doc.story_id);
 }
}

由于没有连接,因此两者的查询速度都非常快。如果您确实需要用户数据或故事数据,CouchDB 支持多文档获取。也相当快,是一种“加入”的方式。

于 2009-11-29T17:50:12.903 回答
0

最近我一直在研究 MongoDB 和 CouchDB,但我的见识有限。尽管如此,在考虑将投票存储在故事文档中时,您可能不得不担心达到 4MB 的文档大小限制。即使您不这样做,您也可能会不断地增加文档的大小以使其移动,从而减慢您的写入速度(请参阅文档在 MongoDB 中的大小)。

对于 CouchDB,一旦计算了视图索引,这些事情就非常简单、优雅并且非常快速。然而,就我个人而言,我对在 CouchDB 中做一个类似的项目犹豫不决,因为基准显示它随着数据库的增长(以及视图索引的增长)逐渐减慢到相当大的程度。我很想看到一些最近的基准测试显示随着数据库大小的增加 CouchDB 的性能。我想尝试 MongoDB 或 CouchDB,但 SQL 似乎仍然如此高效和合乎逻辑,所以我会一直使用它,直到项目正好适合诱惑。

于 2011-07-08T18:45:58.117 回答