这个问题-在Mongo中可以切成薄片吗?讲述了如何在Mongo中获得一小片。总之,使用聚合链$unwind
,$skip
,$limit
,$unwind
,$skip
,$limit
,和$group
。
我的问题是如何在多个文档的集合上执行此操作。我想修剪每个内的嵌套数组。$unwind
但是,只有一次,$skip
并且$limit
仅根据第一个数组的编号才有意义。
有没有一种方法可以在集合中的每个文档上而不是整个集合上运行这种管道?我希望在聚合管道中完成所有工作吗?使用Map-Reduce显然是可能的,但是这样做比分别对$unwind
每个文档运行n + 1个查询要慢。
编辑
以下是示例记录。
{
title: "Text Title"
vtitle: "Text Version Title"
text: [[["Book1, Chapter 1, Line 1", "Book1, Chapter 1, Line 2"],["Book 1, Chapter 2, Line 1"]],[["Book 2, Chapter 1, Line 1]]]
}
此处的记录是一本大书的文本,存储为深度3数组。vtitle
相同的可能有很多不同title
,并且text
可能很大。
我想从许多书籍的集合中的每本书中选择一小部分包含文本的内容,这些内容由索引标识-返回的每个文档的一部分。
例如,输入参数[3,3]
会返回类似以下的记录:
{ "text" : ["Book 4, Chapter 4, Line 1", "Book 4, Chapter 4, Line 2", ...] }
TL; 博士
我认为简短的答案是您还不能真正做到自己想要的。当前的选择是等到v3.1或通过group
聚合对其进行破解(但是我怀疑这对于您的需求而言太慢了)。
理由
尽管还不清楚您想要获得的确切结果,但其目的显然是希望能够在集合中找到一组匹配的文档并转换(即映射)这些文档(通过切片嵌套数组以生成一个固定的字符串列表)。搜索是无关紧要的,因为您可以在映射之前或之后进行搜索,但仍然可以满足您的约束条件。因此,我将只讨论映射。
这是MapReduce的自然用例,但是您已明确将其排除在允许的答案之外。因此,我将依次介绍3个选项。
1)查询
由于您不允许多个查询,因此唯一的选择是在请求中映射数据。这是通过投影运算符处理的。这些将不起作用。
$slice
运算符,但它不处理嵌套数组。$
运营商只允许你参加一个数组,这也不足以阵列中获得一个任意位置的第一个条目。$elemMatch
只允许你从数组中获得一个领域-这也不足以满足您的需求。另外,您不能在查询上链接投影,因此不能以某种狡猾的方式将多个投影放在一起以多次切片数据。
简而言之,这是行不通的。
2)聚合管道
不幸的是,直到v3.1才存在用于聚合管道的分片运算符。因此,您仅限于$ project或其他运算符的狡猾用法(根据您链接的文章)。
首先使用投影算子。虽然您可以对数组字段进行操作,但现在只能获取大小。您可以尝试使用集合逻辑,但是本质上是无序的,因此您无法在此处获得第N个条目。
因此,直接操作显然不起作用。那么,我们可以改善您链接的文章吗?该解决方法仅适用于一个文档,因为您无需区分多个文档。因此,您有能力展开数组以创建更大的文档列表,然后使用文档级范围操作有效地进行切片。
可悲的是,当您需要在最新的展开清单中查找下一个原始文档的开头时,此方法会下降。没有运算符的组合,您无法枚举展开的数组,然后选择该枚举和原始文档。
$unwind
扩展数组,但没有给您索引以供您随后进行匹配,并且$ skip无法提供跳至具有匹配条件的下一个文档的方法。$redact
仍然使您处于原始文档的范围之内,但是又遇到了同样的问题,$project
即无法对嵌套数组进行操作。简而言之,这也是一个失败。
3)群组汇总
在这一点上我将要放弃,然后我注意到了群体聚集。您可以为匹配的文档创建过滤器,但是可以finalize
在返回数据之前提供任意JavaScript函数来转换该数据。这意味着您应该能够发出如下命令:
db.runCommand(
{
group:
{
ns: 'books',
key: { title: 1, text: 1 },
cond: { },
$reduce: function (curr, result) { },
initial: { },
finalize: function(result) {
// Insert your code here to slice the array - e.g.
result.text = result.text[0][0]
}
}
})
当然,如本文所述,如果您的数据库被分片,结果大于16MB或您有超过20,000个文档(因为每个文档现在是聚合的关键),那么这将不起作用。当数据集变大时,它也非常慢。
本文收集自互联网,转载请注明来源。
如有侵权,请联系 [email protected] 删除。
我来说两句