mongo中的稀疏索引和空值

时间:2011-12-22 19:00:29

标签: mongodb indexing mongodb-indexes

我不确定我是否正确理解稀疏索引。

我在fbId上有一个稀疏的唯一索引

{
    "ns" : "mydb.users",
    "key" : {
        "fbId" : 1
    },
    "name" : "fbId_1",
    "unique" : true,
    "sparse" : true,
    "background" : false,
    "v" : 0
}

我希望这会允许我插入带有null的记录作为fbId,但是会抛出重复的键异常。它只允许我在完全删除fbId属性时插入。

是不是应该处理的稀疏索引?

3 个答案:

答案 0 :(得分:34)

稀疏索引不包含错过索引字段的文档。但是,如果字段存在且值为null,则仍会将其编入索引。因此,如果该字段的缺失及其与null的相等性对于您的应用程序看起来相同,并且您希望保持fbId的唯一性,则只有在您拥有它的值之后才能插入它。 / p>

当您拥有大量文档时,您需要稀疏索引,但只有一小部分文档包含某些字段,并且您希望能够通过该字段快速查找文档。创建一个普通的索引太贵了,你只会浪费宝贵的RAM来索引你不感兴趣的文档。

答案 1 :(得分:2)


{a:1, b:5, c:2}
{a:8, b:15, c:7}
{a:4, b:7}
{a:3, b:10}

假设我们希望在上述文档中创建索引。在a&上创建索引b不会成为问题。但是如果我们需要在c上创建索引呢?唯一约束不适用于c键,因为2个文档的空值重复。在这种情况下,解决方案是使用sparse选项。此选项告诉数据库不包含错过密钥的文档。关注的命令是db.collectionName.createIndex({thing:1}, {unique:true, sparse:true})。稀疏索引使我们也可以使用更少的空间。

  

请注意,即使我们有sparse索引,数据库也会执行所有文档扫描,特别是在进行排序时。这可以在explain的结果的获胜计划部分中看到。

答案 2 :(得分:1)

为了确保索引的最大性能,我们可能希望省略索引那些不包含您正在执行索引的字段的文档。为此,MongoDB具有稀疏属性,其工作方式如下:

db.addresses.ensureIndex( { "secondAddress": 1 }, { sparse: true } );

此索引将省略所有不包含secondAddress字段的文档,并且在执行查询时,将永远不会扫描这些文档。

让我分享一下有关基本索引及其一些属性的文章:

地理空间,文本,哈希索引以及唯一和稀疏属性:http://mongodbspain.com/en/2014/02/03/mongodb-indexes-part-2-geospatial-2d-2dsphere/