Docs HomeMongoDB Manual

cursor.sort()

Definition定义

cursor.sort(sort)
Important

mongosh Method

This page documents a mongosh method. This is not the documentation for a language-specific driver, such as Node.js.

For MongoDB API drivers, refer to the language-specific MongoDB driver documentation.

Specifies the order in which the query returns matching documents. 指定查询返回匹配文档的顺序。You must apply sort() to the cursor before retrieving any documents from the database.在从数据库检索任何文档之前,必须对游标应用sort()

The sort() method has the following parameter:sort()方法具有以下参数:

Parameter参数Type类型Description描述
sortdocumentA document that defines the sort order of the result set.定义结果集排序顺序的文档。

The sort parameter contains field and value pairs, in the following form:sort参数包含字段和值对,格式如下:

{ field: value }

The sort document can specify ascending or descending sort on existing fields or sort on text score metadata.排序文档可以在现有字段上指定升序或降序,也可以在文本分数元数据上指定排序

Behavior行为

Limits限制

You can sort on a maximum of 32 keys.最多可以对32个键进行排序。

Sort Consistency排序一致性

Changed in version 4.4.4.4版更改。

MongoDB does not store documents in a collection in a particular order. When sorting on a field which contains duplicate values, documents containing those values may be returned in any order.MongoDB不会按特定顺序将文档存储在集合中。对包含重复值的字段进行排序时,可以按任何顺序返回包含这些值的文档。

If consistent sort order is desired, include at least one field in your sort that contains unique values. The easiest way to guarantee this is to include the _id field in your sort query.如果需要一致的排序顺序,请在排序中至少包含一个包含唯一值的字段。保证这一点的最简单方法是在排序查询中包含_id字段。

Consider the following restaurant collection:考虑以下restaurant集合:

db.restaurants.insertMany( [
{ "_id" : 1, "name" : "Central Park Cafe", "borough" : "Manhattan"},
{ "_id" : 2, "name" : "Rock A Feller Bar and Grill", "borough" : "Queens"},
{ "_id" : 3, "name" : "Empire State Pub", "borough" : "Brooklyn"},
{ "_id" : 4, "name" : "Stan's Pizzaria", "borough" : "Manhattan"},
{ "_id" : 5, "name" : "Jane's Deli", "borough" : "Brooklyn"},
] );

The following command uses the sort() method to sort on the borough field:以下命令使用sort()方法对borough字段进行排序:

db.restaurants.find().sort( { "borough": 1 } )

In this example, sort order may be inconsistent, since the borough field contains duplicate values for both Manhattan and Brooklyn. 在本例中,排序顺序可能不一致,因为borough字段包含ManhattanBrooklyn的重复值。Documents are returned in alphabetical order by borough, but the order of those documents with duplicate values for borough might not be the same across multiple executions of the same sort. For example, here are the results from two different executions of the above command:文档按borough按字母顺序返回,但在同一排序的多个执行中,具有重复borough值的文档的顺序可能不相同。例如,以下是上述命令的两个不同执行的结果:

{ "_id" : 3, "name" : "Empire State Pub", "borough" : "Brooklyn" }
{ "_id" : 5, "name" : "Jane's Deli", "borough" : "Brooklyn" }
{ "_id" : 1, "name" : "Central Park Cafe", "borough" : "Manhattan" }
{ "_id" : 4, "name" : "Stan's Pizzaria", "borough" : "Manhattan" }
{ "_id" : 2, "name" : "Rock A Feller Bar and Grill", "borough" : "Queens" }

{ "_id" : 5, "name" : "Jane's Deli", "borough" : "Brooklyn" }
{ "_id" : 3, "name" : "Empire State Pub", "borough" : "Brooklyn" }
{ "_id" : 4, "name" : "Stan's Pizzaria", "borough" : "Manhattan" }
{ "_id" : 1, "name" : "Central Park Cafe", "borough" : "Manhattan" }
{ "_id" : 2, "name" : "Rock A Feller Bar and Grill", "borough" : "Queens" }

While the values for borough are still sorted in alphabetical order, the order of the documents containing duplicate values for borough (i.e. Manhattan and Brooklyn) is not the same.虽然borough的值仍然按字母顺序排序,但包含borough(即ManhattanBrooklyn)重复值的文档的顺序不同。

To achieve a consistent sort, add a field which contains exclusively unique values to the sort. The following command uses the sort() method to sort on both the borough field and the _id field:要实现一致排序,请在排序中添加一个包含唯一值的字段。以下命令使用sort()方法对borough字段和_id字段进行排序:

db.restaurants.find().sort( { "borough": 1, "_id": 1 } )

Since the _id field is always guaranteed to contain exclusively unique values, the returned sort order will always be the same across multiple executions of the same sort.由于_id字段始终保证包含唯一值,因此在同一排序的多个执行中,返回的排序顺序始终相同。

Ascending/Descending Sort升序/降序排序

Specify in the sort parameter the field or fields to sort by and a value of 1 or -1 to specify an ascending or descending sort respectively.在排序参数中指定要排序的字段,并指定值1-1以分别指定升序或降序。

The following operation sorts the documents first by the age field in descending order and then by the posts field in ascending order:以下操作首先按age字段降序排列文档,然后按posts字段升序排列文档:

db.users.find({ }).sort( { age : -1, posts: 1 } )

When comparing values of different BSON types in sort operations, MongoDB uses the following comparison order, from lowest to highest:在排序操作中比较不同BSON类型的值时,MongoDB使用以下比较顺序,从低到高:

  1. MinKey (internal type)
  2. Null
  3. Numbers (ints, longs, doubles, decimals)
  4. Symbol, String
  5. Object
  6. Array
  7. BinData
  8. ObjectId
  9. Boolean
  10. Date
  11. Timestamp
  12. Regular Expression
  13. MaxKey (internal type)

For details on the comparison/sort order for specific types, see Comparison/Sort Order.有关特定类型的比较/排序顺序的详细信息,请参阅比较/排序次序

Text Score Metadata Sort文本分数元数据排序

For a $text search, you can sort by descending relevance score using the { $meta: "textScore" } expression.对于$text搜索,可以使用{ $meta: "textScore" }表达式按相关性分数降序进行排序。

The following sample document specifies a descending sort by the "textScore" metadata:以下示例文档按照"textScore"元数据指定降序:

db.users.find(
{ $text: { $search: "operating" } },
{ score: { $meta: "textScore" }} // Optional starting in MongoDB 4.4
).sort({ score: { $meta: "textScore" } })

The "textScore" metadata sorts in descending order."textScore"元数据按降序排序。

For more information, see $meta for details.有关详细信息,请参阅$meta

Sort and Index Use排序和索引使用

MongoDB can obtain the results of a sort operation from an index which includes the sort fields. MongoDB可以从包含排序字段的索引中获得排序操作的结果。MongoDB may use multiple indexes to support a sort operation if the sort uses the same indexes as the query predicate.如果排序使用与查询谓词相同的索引,MongoDB可能会使用多个索引来支持一个排序操作。

If MongoDB cannot use an index or indexes to obtain the sort order, MongoDB must perform a blocking sort operation on the data. 如果MongoDB不能使用一个或多个索引来获得排序顺序,那么MongoDB必须对数据执行阻塞排序操作。A blocking sort indicates that MongoDB must consume and process all input documents to the sort before returning results. Blocking sorts do not block concurrent operations on the collection or database.阻塞排序表示MongoDB在返回结果之前必须使用并处理所有输入文档以进行排序。阻止排序不会阻止对集合或数据库的并发操作。

Sort operations that use an index often have better performance than blocking sorts. 使用索引的排序操作通常比阻塞排序具有更好的性能。For more information on creating indexes to support sort operations, see Use Indexes to Sort Query Results.有关创建索引以支持排序操作的详细信息,请参阅使用索引对查询结果进行排序

If MongoDB requires using more than 100 megabytes of system memory for the blocking sort operation, MongoDB returns an error unless the query specifies cursor.allowDiskUse() (New in MongoDB 4.4). 如果MongoDB需要使用超过100兆字节的系统内存进行阻塞排序操作,则除非查询指定cursor.allowDiskUse(),否则MongoDB将返回错误(MongoDB 4.4中的新增)。allowDiskUse() allows MongoDB to use temporary files on disk to store data exceeding the 100 megabyte system memory limit while processing a blocking sort operation.允许MongoDB在处理阻塞排序操作时使用磁盘上的临时文件来存储超过100兆字节系统内存限制的数据。

To check if MongoDB must perform a blocking sort, append cursor.explain() to the query and check the explain results. 要检查MongoDB是否必须执行阻塞排序,请将cursor.explain()附加到查询并检查解释结果If the query plan contains a SORT stage, then MongoDB must perform a blocking sort operation subject to the 100 megabyte memory limit.如果查询计划包含SORT阶段,那么MongoDB必须执行一个受100兆字节内存限制的阻塞排序操作。

To prevent blocking sorts from consuming too much memory:要防止阻塞排序占用过多内存,请执行以下操作:

Limit Results限制结果

You can use sort() in conjunction with limit() to return the first (in terms of the sort order) k documents, where k is the specified limit.您可以将sort()limit()结合使用来返回第一个(根据排序顺序)k个文档,其中k是指定的限制。

If MongoDB cannot obtain the sort order via an index scan, then MongoDB uses a top-k sort algorithm. 如果MongoDB无法通过索引扫描获得排序顺序,那么MongoDB将使用top-k排序算法。This algorithm buffers the first k results (or last, depending on the sort order) seen so far by the underlying index or collection access. 该算法缓冲底层索引或集合访问迄今为止看到的前k个结果(或最后一个,取决于排序顺序)。If at any point the memory footprint of these k results exceeds 100 megabytes, the query will fail unless the query specifies cursor.allowDiskUse() (New in MongoDB 4.4).如果在任何时候,这k个结果的内存占用超过100兆字节,则除非查询指定cursor.allowDiskUse()MongoDB 4.4中的新增),否则查询将失败。

Interaction with Projection与投影的交互

When a set of results are both sorted and projected, the MongoDB query engine will always apply the sorting first.当对一组结果进行排序和投影时,MongoDB查询引擎将始终首先应用排序。

Examples实例

A collection orders contain the following documents:集合orders包含以下文档:

{ _id: 1, item: { category: "cake", type: "chiffon" }, amount: 10 }
{ _id: 2, item: { category: "cookies", type: "chocolate chip" }, amount: 50 }
{ _id: 3, item: { category: "cookies", type: "chocolate chip" }, amount: 15 }
{ _id: 4, item: { category: "cake", type: "lemon" }, amount: 30 }
{ _id: 5, item: { category: "cake", type: "carrot" }, amount: 20 }
{ _id: 6, item: { category: "brownies", type: "blondie" }, amount: 10 }

The following query, which returns all documents from the orders collection, does not specify a sort order:以下查询返回orders集合中的所有文档,但未指定排序顺序:

db.orders.find()

The query returns the documents in indeterminate order:查询以不确定的顺序返回文档:

{ "_id" : 1, "item" : { "category" : "cake", "type" : "chiffon" }, "amount" : 10 }
{ "_id" : 2, "item" : { "category" : "cookies", "type" : "chocolate chip" }, "amount" : 50 }
{ "_id" : 3, "item" : { "category" : "cookies", "type" : "chocolate chip" }, "amount" : 15 }
{ "_id" : 4, "item" : { "category" : "cake", "type" : "lemon" }, "amount" : 30 }
{ "_id" : 5, "item" : { "category" : "cake", "type" : "carrot" }, "amount" : 20 }
{ "_id" : 6, "item" : { "category" : "brownies", "type" : "blondie" }, "amount" : 10 }

The following query specifies a sort on the amount field in descending order.以下查询按降序指定amount字段的排序。

db.orders.find().sort( { amount: -1 } )

The query returns the following documents, in descending order of amount:查询按amount降序返回以下文档:

{ "_id" : 2, "item" : { "category" : "cookies", "type" : "chocolate chip" }, "amount" : 50 }
{ "_id" : 4, "item" : { "category" : "cake", "type" : "lemon" }, "amount" : 30 }
{ "_id" : 5, "item" : { "category" : "cake", "type" : "carrot" }, "amount" : 20 }
{ "_id" : 3, "item" : { "category" : "cookies", "type" : "chocolate chip" }, "amount" : 15 }
{ "_id" : 1, "item" : { "category" : "cake", "type" : "chiffon" }, "amount" : 10 }
{ "_id" : 6, "item" : { "category" : "brownies", "type" : "blondie" }, "amount" : 10 }

The following query specifies the sort order using the fields from an embedded document item. 以下查询使用嵌入文档item中的字段指定排序顺序。The query sorts first by the category field in ascending order, and then within each category, by the type field in ascending order.查询首先按category字段升序排序,然后在每个category中按type字段升序排序。

db.orders.find().sort( { "item.category": 1, "item.type": 1 } )

The query returns the following documents, ordered first by the category field, and within each category, by the type field:查询返回以下文档,这些文档首先按category字段排序,然后在每个类别中按type字段排序:

{ "_id" : 6, "item" : { "category" : "brownies", "type" : "blondie" }, "amount" : 10 }
{ "_id" : 5, "item" : { "category" : "cake", "type" : "carrot" }, "amount" : 20 }
{ "_id" : 1, "item" : { "category" : "cake", "type" : "chiffon" }, "amount" : 10 }
{ "_id" : 4, "item" : { "category" : "cake", "type" : "lemon" }, "amount" : 30 }
{ "_id" : 2, "item" : { "category" : "cookies", "type" : "chocolate chip" }, "amount" : 50 }
{ "_id" : 3, "item" : { "category" : "cookies", "type" : "chocolate chip" }, "amount" : 15 }

Return in Natural Order按自然顺序返回

The $natural parameter returns items according to their natural order within the database. $natural参数根据项目在数据库中的自然顺序返回项目。This ordering is an internal implementation feature, and you should not rely on any particular ordering of the documents.这种排序是一种内部实现功能,您不应该依赖于文档的任何特定排序。

Index Use索引使用

Queries that include a sort by $natural order do not use indexes to fulfill the query predicate with the following exception: If the query predicate is an equality condition on the _id field { _id: <value> }, then the query with the sort by $natural order can use the _id index.包含按$natural顺序排序的查询不使用索引来实现查询谓词,但以下情况除外:如果查询谓词是_id字段{ _id: <value> }上的相等条件,则按$national排序的查询可以使用_id索引。

Tip

See also: 另请参阅:

$natural