文档计数
模板 API 提供了多种方法来计算符合给定条件的文档数量。下面将介绍其中一种方法。
template.query(Person.class)
.matching(query(where("firstname").is("luke")))
.count();
在 SpringData MongoDB 3.x 之前的版本中,计数操作使用了 MongoDB 的内部集合统计信息。随着 MongoDB 事务 的引入,这不再可能,因为统计信息无法正确反映事务期间可能发生的变化,因此需要基于聚合的计数方法。所以在 2.x 版本中,如果没有事务在进行,MongoOperations.count()
会使用集合统计信息,否则会使用聚合变体。
自 Spring Data MongoDB 3.x 起,任何 count
操作无论是否存在过滤条件,都会通过 MongoDB 的 countDocuments
使用基于聚合的计数方法。如果应用程序能够接受基于集合统计的限制,MongoOperations.estimatedCount()
提供了一个替代方案。
通过将 MongoTemplate#useEstimatedCount(…)
设置为 true
,MongoTemplate#count(…) 操作(使用空过滤查询时)将被委托给 estimatedCount
,前提是没有活跃的事务且模板未绑定到 session。仍然可以通过 MongoTemplate#exactCount
获取精确的数字,但使用 estimatedCount
可以加快操作速度。
MongoDB 原生的 countDocuments
方法和 $match
聚合操作不支持 $near
和 $nearSphere
,而是需要 $geoWithin
与 $center
或 $centerSphere
配合使用,而后者不支持 $minDistance
(参见 jira.mongodb.org/browse/SERVER-37043)。
因此,在使用 Reactive
-/MongoTemplate
进行 count
操作时,给定的 Query
将被重写以绕过该问题,如下所示。
{ location : { $near : [-73.99171, 40.738868], $maxDistance : 1.1 } } 1
{ location : { $geoWithin : { $center: [ [-73.99171, 40.738868], 1.1] } } } 2
{ location : { $near : [-73.99171, 40.738868], $minDistance : 0.1, $maxDistance : 1.1 } } 3
{$and :[ { $nor :[ { location :{ $geoWithin :{ $center :[ [-73.99171, 40.738868 ], 0.01] } } } ]}, { location :{ $geoWithin :{ $center :[ [-73.99171, 40.738868 ], 1.1] } } } ] } 4
使用
$near
的计数源查询。重写后的查询,现在使用
$geoWithin
与$center
。使用
$near
并带有$minDistance
和$maxDistance
的计数源查询。重写后的查询,现在结合了
$nor
和$geowithin
条件,以绕过不支持的$minDistance
。