2

所以我需要在 MongoDB 中创建一个查找集合来验证唯一性。要求是检查是否重复了相同的 2 个值。在 SQL 中,我会这样

SELECT count(id) WHERE key1 = 'value1' AND key2 = 'value2'

如果上述查询返回一个计数,则表示该组合不是唯一的。我有两种解决方案,但我不确定哪一种更具可扩展性。我需要针对 30M+ 文档创建此映射。

解决方案1:

我在 key1 和 key2 上创建了一个带有复合索引的文档集合

{
  _id: <MongoID>,
  key1: <value1>,
  key2: <value2>
}

解决方案2:

我编写应用程序逻辑以通过连接 value1 和 value2 创建自定义 _id

{
  _id: <value1>_<value2>
}

就个人而言,我觉得第二个更优化,因为它只有一个索引,而且 doc 的大小也更小。但我不确定创建自己的 _id 索引是否是一个好习惯,因为它们可能不是完全随机的。你怎么看?

提前致谢。

更新:

我的数据库已经有很多占用内存的索引,所以我想将索引大小保持在尽可能低的水平,特别是对于仅用于验证唯一性的集合。

4

2 回答 2

2

我建议解决方案 1,即使用复合索引并使用两个不同的属性 key1 和 key2

db.yourCollection.ensureIndex( { "key1": 1, "key2": 1 }, { unique: true } )
  1. 如果需要,您可以通过单个字段轻松搜索。即,如果您只需要通过 key1 或 key2 进行搜索,那么使用复合索引会很容易。如果您_id使用组合键进行操作,则很难按单个字段进行搜索。
  2. 在设计文档时,Mongo 中的文档大小是最不被打扰的。
  3. 如果在不久的将来,如果您需要更改同一文档的键值相对于其他值,那将很容易。请记住,如果您在其他集合的文档中使用此文档的引用。
  4. 就您的可扩展性而言,_id 索引将是顺序的、易于分片的,并且您可以让 MongoDB 管理它。
  5. 如果您使用这些键进行搜索,那么它将使用该索引,否则它将使用其他所需的索引进行搜索。

如果您仍然在考虑文档的大小而不是搜索,那么您可以使用解决方案 1,使 _id 像

{_id:{key1:<value1>,key2:<value2>}}

这样你也可以搜索特定的 _id.key1 。

更新:

是的,如果您关心的是文档大小而不是维护。如果您确定键在同一文档的未来不会修改,并且如果它仍在修改并且在其他集合中没有引用,那么您可以使用解决方案 1。只需使用键作为对象而不是下划线_。如果将来需要,您也可以稍后添加更多密钥。

于 2016-08-09T12:23:56.437 回答
1

我认为解决方案 2 更适合您的要求。生成 MongoDB 的 _id 值是绝对可以的。大多数应用程序确实使用 UUID 填充 _id 值。在您的情况下,假设此集合主要用于验证唯一性(即临时表的种类)或查找目的,则为 _id 值连接值 1 和 2 是有意义的。

解决方案 1很昂贵,因为它需要额外的索引。同样,这取决于您是要使用此集合来单独验证唯一性目的还是将其用于其他用例。

请注意,您需要创建唯一的复合索引,以便它不允许插入重复值的数据。

于 2016-08-09T12:29:21.080 回答