- mongodb - 在 MongoDB mapreduce 中,如何展平值对象?
- javascript - 对象传播与 Object.assign
- html - 输入类型 ="submit"Vs 按钮标签它们可以互换吗?
- sql - 使用 MongoDB 而不是 MS SQL Server 的优缺点
我有这三个 MongoDB 文档:
{
"_id" : ObjectId("571094afc2bcfe430ddd0815"),
"name" : "Barry",
"surname" : "Allen",
"address" : [
{
"street" : "Red",
"number" : NumberInt(66),
"city" : "Central City"
},
{
"street" : "Yellow",
"number" : NumberInt(7),
"city" : "Gotham City"
}
]
}
{
"_id" : ObjectId("57109504c2bcfe430ddd0816"),
"name" : "Oliver",
"surname" : "Queen",
"address" : {
"street" : "Green",
"number" : NumberInt(66),
"city" : "Star City"
}
}
{
"_id" : ObjectId("5710953ac2bcfe430ddd0817"),
"name" : "Tudof",
"surname" : "Unknown",
"address" : "homeless"
}
address
字段是第一个文档中的对象的 Array
、第二个文档中的 Object
和 String
在第三。我的目标是找出我的集合中有多少文档包含字段 address.street
。在这种情况下,正确的计数是 1,但通过我的查询,我得到了两个:
db.coll.find({"address.street":{"$exists":1}}).count()
我也尝试过 map/reduce。它有效,但速度较慢;所以如果可能的话,我会避免它。
最佳答案
这里的区别在于 .count()
操作在返回字段存在的“文档”计数时实际上是“正确的”。因此,一般考虑可分解为:
那么最有效的方法是排除那些“街道”是“地址”属性的文档作为“数组”,然后只需使用查找 0
的点符号属性> 排除项中不存在的索引:
db.coll.find({
"address.street": { "$exists": true },
"address.0": { "$exists": false }
}).count()
在这两种情况下,$exists
都作为 native 编码的运算符测试执行正确且高效的工作。
如果您实际询问的是“字段计数”,其中一些“文档”包含数组条目,其中该“字段”可能出现多次。
为此,您需要您提到的聚合框架或 mapReduce。 MapReduce 使用基于 JavaScript 的处理,因此比 .count()
操作要慢得多。聚合框架还需要计算并且“将”比 .count()
慢,但不会像 mapReduce 那么多。
在 MongoDB 3.2 中,您可以通过 $sum
的扩展功能获得一些帮助处理一组值以及作为分组累加器。这里的另一个助手是 $isArray
允许通过 $map
使用不同的处理方法当数据实际上是“一个数组”时:
db.coll.aggregate([
{ "$group": {
"_id": null,
"count": {
"$sum": {
"$sum": {
"$cond": {
"if": { "$isArray": "$address" },
"then": {
"$map": {
"input": "$address",
"as": "el",
"in": {
"$cond": {
"if": { "$ifNull": [ "$$el.street", false ] },
"then": 1,
"else": 0
}
}
}
},
"else": {
"$cond": {
"if": { "$ifNull": [ "$address.street", false ] },
"then": 1,
"else": 0
}
}
}
}
}
}
}}
])
早期版本依赖于更多的条件处理,以便以不同方式处理数组和非数组数据,通常需要 $unwind
处理数组条目。
通过 $map
转置数组使用 MongoDB 2.6:
db.coll.aggregate([
{ "$project": {
"address": {
"$cond": {
"if": { "$ifNull": [ "$address.0", false ] },
"then": "$address",
"else": {
"$map": {
"input": ["A"],
"as": "el",
"in": "$address"
}
}
}
}
}},
{ "$unwind": "$address" },
{ "$group": {
"_id": null,
"count": {
"$sum": {
"$cond": {
"if": { "$ifNull": [ "$address.street", false ] },
"then": 1,
"else": 0
}
}
}
}}
])
或者使用 MongoDB 2.2 或 2.4 提供条件选择:
db.coll.aggregate([
{ "$group": {
"_id": "$_id",
"address": {
"$first": {
"$cond": [
{ "$ifNull": [ "$address.0", false ] },
"$address",
{ "$const": [null] }
]
}
},
"other": {
"$push": {
"$cond": [
{ "$ifNull": [ "$address.0", false ] },
null,
"$address"
]
}
},
"has": {
"$first": {
"$cond": [
{ "$ifNull": [ "$address.0", false ] },
1,
0
]
}
}
}},
{ "$unwind": "$address" },
{ "$unwind": "$other" },
{ "$group": {
"_id": null,
"count": {
"$sum": {
"$cond": [
{ "$eq": [ "$has", 1 ] },
{ "$cond": [
{ "$ifNull": [ "$address.street", false ] },
1,
0
]},
{ "$cond": [
{ "$ifNull": [ "$other.street", false ] },
1,
0
]}
]
}
}
}}
])
所以后一种形式“应该”比 mapReduce 表现好一点,但可能不会好很多。
在所有情况下,逻辑都归结为使用 $ifNull
作为聚合框架的 $exists
的“逻辑”形式。与 $cond
配对,当属性实际存在时得到一个“truthfull”结果,不存在时返回一个false
值。这决定了是1
还是0
分别通过$sum
返回到整体累加中。 .
理想情况下,您拥有可以在单个 $group
中执行此操作的现代版本管道阶段,否则您需要更长的路径。
关于mongodb - 计算有多少文档包含一个字段,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36645838/
我有一个类似于以下的结构。 class A { string title; List bItem; } class B { int pric
本地流 和 远程流 两者都是“媒体流列表 ”。 本地流 包含“本地媒体流 ” 对象 但是,远程流 包含“媒体流 ” 对象 为什么差别这么大? 当我使用“本地流 “- 这个对我有用: localVide
我正在尝试将 8 列虚拟变量转换为 8 级排名的一列。 我试图用这个公式来做到这一点: =IF(OR(A1="1");"1";IF(OR(B1="1");"2";IF(OR(C1="1");"3";I
我正在使用面向对象编程在 Python 中创建一个有点复杂的棋盘游戏的实现。 我的问题是,许多这些对象应该能够与其他对象交互,即使它们不包含在其中。 例如Game是一个对象,其中包含PointTrac
有没有办法获取与 contains 语句匹配的最深元素? 基本上,如果我有嵌套的 div,我想要最后一个元素而不是父元素: Needle $("div:contains('Needle')")
出于某种原因,我无法在 Google 上找到答案!但是使用 SQL contains 函数我怎么能告诉它从字符串的开头开始,即我正在寻找等同于的全文 喜欢 'some_term%'。 我知道我可以使用
我正在尝试创建一个正则表达式来匹配具有 3 个或更多元音的字符串。 我试过这个: [aeiou]{3,} 但它仅在元音按顺序排列时才有效。有什么建议吗? 例如: 塞缪尔 -> 有效 琼 -> 无效 S
嘿所以我遇到了这样的情况,我从数据库中拉回一个客户,并通过包含的方式包含所有案例研究 return (from c in db.Clients.Include("CaseStudies")
如果关键字是子字符串,我无法弄清楚为什么这个函数不返回结果。 const string = 'cake'; const substring = 'cak'; console.log(string.in
我正在尝试将包含特定文本字符串的任何元素更改为红色。在我的示例中,我可以将子元素变为蓝色,但是我编写“替换我”行的方式有些不正确;红色不会发生变化。我注意到“contains”方法通常写为 :cont
我想问一下我是否可以要求/包含一个语法错误的文件,如果不能,则require/include返回一个值,这样我就知道所需/包含的文件存在语法错误并且不能被要求/包含? file.php语法错误 inc
我想为所有包含youtube链接的链接添加一个rel。 这就是我正在使用的东西-但它没有用。有任何想法吗? $('a [href:contains(“youtube.com”)]')。attr('re
我正在尝试在 Elasticsearch 中查询。除搜索中出现“/”外,此功能均正常运行。查询如下所示 GET styling_rules/product_line_filters/_search {
我正在开发名为eBookRepository的ASP.NET MVC应用程序,其中包含在线图书。 电子书具有自己的标题,作者等。因此,现在我正在尝试实现搜索机制。我必须使用Elasticsearch作
我已阅读Firebase Documentation并且不明白什么是 .contains()。 以下是文档中 Firebase 数据库的示例规则: { "rules": { "rooms"
我的问题是我可以给出条件[ 'BookTitleMaster.id' => $xtitid, ] 如下所示 $bbookinfs = $this->BookStockin->BookIssue->fi
我需要能够使用 | 检查模式在他们中。例如,对于像“dtest|test”这样的字符串,像 d*|*t 这样的表达式应该返回 true。 我不是正则表达式英雄,所以我只是尝试了一些事情,例如: Reg
我想创建一个正则表达式来不匹配某些单词... 我的字符:var test = "é123rr;and;ià456;or;456543" 我的正则表达式:test.match(\((?!and)(?!o
我在 XSLT 中有一个名为 variable_name 的变量,如果相关产品具有名称为 A 或 B 或两者均为 A & 的属性,我将尝试将其设置为 1 B.
您好,我想让接待员和经理能够查看工作类型和费率并随后进行更新。但是技术人员只能查看不能更新。该图是否有效? 我读到扩展用例是由发起基本用例的参与者发起的。我应该如何区分技术人员只能启动基本案例而不能启
我是一名优秀的程序员,十分优秀!