在MongoDB中存储null与不存储密钥

Zai*_*sud 43 mongodb nosql document-database mongodb-query

在我看来,当你创建一个Mongo文档并且有一个{key, value}有时没有值的字段时,你有两个选择:

  1. {key, null}即在字段中写入空值
  2. 根本不要将密钥存储在该文档中

这两个选项都很容易查询,您可以在其中查询,{key : null}另一个查询{key : {$exists : false}}.

我真的不能想到在应用程序场景中会产生任何影响的两个选项之间的任何差异(除了选项2的存储略少).

任何人都可以告诉我,如果有任何理由,人们会更喜欢这两种方法中的任何一种,为什么呢?

编辑

在提出问题之后,我也发现在这两种情况下索引可能表现不同,即可以为选项2创建稀疏索引,但我仍然试图比较并理解两种方法中完整索引的考虑因素.

Alp*_*haB 35

的确,你还有第三种可能性:( key: ""空值)

而你忘记了关于空值的特殊性.查询 key: null将检索所有密钥为空密钥不存在的文档.

当查询$exists:false将仅检索其中字段键不存在的doc时.

要回到您的确切问题,这取决于您的查询和数据代表什么.如果你需要保留它,例如,用户设置一个值然后取消设置它,你应该将该字段保持为null或为空.如果您不需要,可以删除此字段.

  • 我会远离钥匙:""因为这意味着它是一个字符串.如果您检索此类字段并执行类似isKeyExists(key)的操作,则即使它是空字符串,也会传递为true.所以,假设您期望布尔值存在错误空间. (12认同)

Sam*_*cía 16

请注意,由于MongoDB不使用字段名字典压缩,因此field:null占用磁盘空间和RAM,而根本不存储密钥并不占用资源.

  • 这个答案在2018年仍然有效吗? (10认同)
  • 这么晚才回复很抱歉!我不认为情况仍然如此。启用 WiredTiger 存储和快速压缩后,我认为它不应该引起注意。 (2认同)

Sam*_*aye 7

这真的归结为:

  • 你的场景
  • 你的查询方式
  • 你的索引需要
  • 你的语言

我个人已选择存储空键.它使我可以更轻松地集成到我的应用程序中.我使用PHP与Active Record和uisng null值使我的生活变得更加容易,因为我不必在应用程序上加上字段加速的压力.此外,我不需要制作任何复杂的代码来处理魔法设置不存在的变量.

我个人不会像存储空值"",因为如果你不小心,你可以有两个空值null"",然后你就会有专门查询的HAP-危险时间.所以我个人更喜欢null空值.

至于空间和索引:它取决于有多少行可能没有这个列但我怀疑你会真正注意到索引大小的增加是由于一些额外的文档带有null.我的意思是存储的差异是很少的,特别是如果相应的键名也很小.这也适用于大型设置.

我很坦率地不确定它之间的索引用法$exists,null但是null可能是一个更标准化的方法来查询存在,因为记住MongoDB是无模式的,这意味着你不需要在doc中再生成两个空值的那个字段:不存在和null.最好选择其中一个.

我选择null.