投影构建器
Overview
在本指南中,您可以学习;了解如何在MongoDB Java驾驶员中使用 构建者 指定 投影 。
MongoDB 支持字段投影,可指定在返回查询结果时包含和排除哪些字段。MongoDB 中的投影遵循一些基本规则:
除非明确排除,否则
_id
字段始终包含在内指定要包含的字段将隐式排除
_id
字段以外的所有其他字段指定排除字段只会删除查询结果中的该字段
在此处查找有关投影机制的更多信息。
Projections
类为所有 MongoDB 投影操作符提供静态工厂方法。每个方法都返回一个 BSON 类型的实例,您可以将其传递给任何需要投影的方法。
样本文档和示例
以下部分介绍了对名为projection_builders
的示例集合运行查询和投影操作的示例。每个部分都使用一个名为 collection
的变量来引用 projection_builders
集合的MongoCollection
实例。
该集合包含以下文档,代表了 2018 年和 2019 年的月平均气温(摄氏度):
{ "year" : 2018, "type" : "even number but not a leap year", "temperatures" : [ { "month" : "January", "avg" : 9.765 }, { "month" : "February", "avg" : 9.675 }, { "month" : "March", "avg" : 10.004 }, { "month" : "April", "avg" : 9.983 }, { "month" : "May", "avg" : 9.747 }, { "month" : "June", "avg" : 9.65 }, { "month" : "July", "avg" : 9.786 }, { "month" : "August", "avg" : 9.617 }, { "month" : "September", "avg" : 9.51 }, { "month" : "October", "avg" : 10.042 }, { "month" : "November", "avg" : 9.452 }, { "month" : "December", "avg" : 9.86 } ] }, { "year" : 2019, "type" : "odd number, can't be a leap year", "temperatures" : [ { "month" : "January", "avg" : 10.023 }, { "month" : "February", "avg" : 9.808 }, { "month" : "March", "avg" : 10.43 }, { "month" : "April", "avg" : 10.175 }, { "month" : "May", "avg" : 9.648 }, { "month" : "June", "avg" : 9.686 }, { "month" : "July", "avg" : 9.794 }, { "month" : "August", "avg" : 9.741 }, { "month" : "September", "avg" : 9.84 }, { "month" : "October", "avg" : 10.15 }, { "month" : "November", "avg" : 9.84 }, { "month" : "December", "avg" : 10.366 } ] }
投影操作
以下各节包含可用投影操作以及使用Projections
类构建这些操作的相关信息。
包含
使用 include()
方法指定包含一个或多个字段。
以下示例包括 year
字段和(隐式的)_id
字段:
Bson filter = Filters.empty(); Bson projection = include("year"); collection.find(filter).projection(projection).forEach(doc -> System.out.println(doc.toJson()));
以下代码显示此投影的输出:
{"_id": {"$oid": "6042edc9f2b56342164e0790"}, "year": 2018} {"_id": {"$oid": "6042edc9f2b56342164e0791"}, "year": 2019}
以下示例包括 year
和 type
字段以及(隐式的)_id
字段:
Bson filter = Filters.empty(); Bson projection = include("year", "type"); collection.find(filter).projection(projection).forEach(doc -> System.out.println(doc.toJson()));
以下代码显示此投影的输出:
{"_id": {"$oid": "6042edc9f2b56342164e0790"}, "year": 2018, "type": "even number but not a leap year"} {"_id": {"$oid": "6042edc9f2b56342164e0791"}, "year": 2019, "type": "odd number, can't be a leap year"}
Exclusion
使用 exclude()
方法指定排除一个或多个字段。
以下示例排除了 temperatures
(温度)字段:
Bson filter = Filters.empty(); Bson projection = exclude("temperatures"); collection.find(filter).projection(projection).forEach(doc -> System.out.println(doc.toJson()));
以下代码显示此投影的输出:
{"_id": {"$oid": "6042edc9f2b56342164e0790"}, "year": 2018, "type": "even number but not a leap year"} {"_id": {"$oid": "6042edc9f2b56342164e0791"}, "year": 2019, "type": "odd number, can't be a leap year"}
以下示例排除了type
和temperatures
字段:
Bson filter = Filters.empty(); Bson projection = exclude("temperatures", "type"); collection.find(filter).projection(projection).forEach(doc -> System.out.println(doc.toJson()));
以下代码显示此投影的输出:
{"_id": {"$oid": "6042edc9f2b56342164e0790"}, "year": 2018} {"_id": {"$oid": "6042edc9f2b56342164e0791"}, "year": 2019}
合并投影
使用 fields()
方法合并多个投影。
以下示例包括 year
和 type
字段,不包括 _id
字段:
Bson filter = Filters.empty(); Bson projection = fields(include("year", "type"), exclude("_id")); collection.find(filter).projection(projection).forEach(doc -> System.out.println(doc.toJson()));
以下代码显示此投影的输出:
{"year": 2018, "type": "even number but not a leap year"} {"year": 2019, "type": "odd number, can't be a leap year"}
排除 _id
使用 excludeId()
便捷方法指定排除 _id
字段:
Bson filter = Filters.empty(); Bson projection = fields(include("year", "type"), excludeId()); collection.find(filter).projection(projection).forEach(doc -> System.out.println(doc.toJson()));
以下代码显示此投影的输出:
{"year": 2018, "type": "even number but not a leap year"} {"year": 2019, "type": "odd number, can't be a leap year"}
投影数组元素匹配
使用elemMatch(String, Bson)
方法变体指定一个数组投影,该投影将包含与所提供的查询筛选器匹配的数组的第一个元素。在检索到与查询筛选器(如提供)匹配的所有文档后,会发生此筛选。
注意
无论有多少个匹配项,都只包含与指定查询筛选器匹配的第一个元素。
以下示例投影 temperatures
数组的第一个元素,其中 avg
字段大于 10.1
:
Bson filter = Filters.empty(); Bson projection = fields(include("year"), elemMatch("temperatures", Filters.gt("avg", 10.1))); collection.find(filter).projection(projection).forEach(doc -> System.out.println(doc.toJson()));
以下代码显示此投影的输出:
{"_id": {"$oid": "6042edc9f2b56342164e0790"}, "year": 2018} {"_id": {"$oid": "6042edc9f2b56342164e0791"}, "year": 2019, "temperatures": [{"month": "March", "avg": 10.43}]}
在操作的查询部分指定匹配条件后,使用 elemMatch(String)
方法变体指定位置投影以包含数组的第一个元素。只有与查询筛选条件匹配的文档才会被检索。
重要
在 MongoDB 4.4 版本中,指定的数组字段必须出现在查询筛选器中。从 MongoDB 4.4 开始,您可以对未出现在查询筛选器中的数组字段使用位置投影。
以下示例投影 temperatures
数组的第一个元素:
Bson filter = Filters.gt("temperatures.avg", 10.1); Bson projection = fields(include("year"), elemMatch("temperatures")); collection.find(filter).projection(projection).forEach(doc -> System.out.println(doc.toJson()));
以下代码显示此投影的输出:
{"_id": {"$oid": "6042edc9f2b56342164e0791"}, "year": 2019, "temperatures": [{"month": "March", "avg": 10.43}]}
投影数组切片
使用 slice()
方法投影数组片段。
以下示例投影 temperatures
数组的前 6 个元素:
Bson filter = Filters.empty(); // first half of the year Bson projection = slice("temperatures", 6); collection.find(filter).projection(projection) .forEach(doc -> System.out.println(doc.toJson(JsonWriterSettings.builder().indent(true).build())));
以下代码显示此投影的输出:
{ "_id": { "$oid": "6042f1bc8ee6fa2a84d2be69" }, "year": 2018, "type": "even number but not a leap year", "temperatures": [ ... <January-June temperature nested documents> ] } { "_id": { "$oid": "6042f1bc8ee6fa2a84d2be6a" }, "year": 2019, "type": "odd number, can't be a leap year", "temperatures": [ ... <January-June temperature nested documents> ] }
以下示例跳过 temperatures
数组的前 6 个元素,投影接下来的 6 个元素:
Bson filter = Filters.empty(); // second half of the year Bson projection = slice("temperatures", 6, 6); collection.find(filter).projection(projection) .forEach(doc -> System.out.println(doc.toJson(JsonWriterSettings.builder().indent(true).build())));
以下代码显示此投影的输出:
{ "_id": { "$oid": "6042f1bc8ee6fa2a84d2be69" }, "year": 2018, "type": "even number but not a leap year", "temperatures": [ ... <July-December temperature nested documents> ] } { "_id": { "$oid": "6042f1bc8ee6fa2a84d2be6a" }, "year": 2019, "type": "odd number, can't be a leap year", "temperatures": [ ... <July-December temperature nested documents> ] }
投影文本分数
使用metaTextScore()
方法指定文本查询分数的投影
以下示例将文本得分投影为 score
字段的值:
Bson filter = Filters.text("even number"); Bson projection = fields(include("year"), metaTextScore("score")); collection.find(filter).projection(projection).forEach(doc -> System.out.println(doc.toJson()));
以下代码显示此投影的输出:
{"_id": {"$oid": "6042f1bc8ee6fa2a84d2be69"}, "year": 2018, "score": 1.25} {"_id": {"$oid": "6042f1bc8ee6fa2a84d2be6a"}, "year": 2019, "score": 0.625}