$sortArray (aggregation)

On this page本页内容

Definition定义

$sortArray

New in version 5.2.在版本5.2中新增

Sorts an array based on its elements. 根据数组的元素对数组进行排序。The sort order is user specified.排序顺序由用户指定。

$sortArray has the following syntax:语法如下:

$sortArray: {
   input: <array>,
   sortBy: <sort spec>
}
Field字段Type类型Description描述
inputexpression表达式

The array to be sorted.要排序的数组。

The result is null if the expression:如果表达式出现如下情况,结果为null

  • is missing缺失
  • evaluates to 计算结果为null
  • evaluates to 计算结果为undefined

If the expression evaluates to any other non-array value, the document returns an error.如果表达式的计算结果为任何其他非数组值,文档将返回错误。

sortBydocumentThe document specifies a sort ordering.文档指定排序顺序。

Behavior行为

The $sortArray expression orders the input array according to the sortBy specification.$sortArray表达式根据sortBy规范对input数组排序。

The $sortArray syntax and semantics are the same as the behavior in a $push operation modified by $sort.$sortArray语法和语义与$sort修改的$push操作中的行为相同。

Sort by Document Fields按文档字段排序

If the array elements are documents, you can sort by a document field. 如果数组元素是文档,则可以按文档字段排序。Specify the field name and a sort direction, ascending (1), or descending (-1 ).指定字段名称和排序方向,升序(1)或降序(-1)。

{
   input: <array-of-documents>,
   sortBy: { <document-field>: {sort-direction> }
}

Sort by Value按值排序

To sort the whole array by value, or to sort by array elements that are not documents, identify the input array and specify 1 for an ascending sort or -1 for descending sort in the sortBy parameter.要按值对整个数组进行排序,或按非文档的数组元素进行排序,请标识输入数组,并在sortBy参数中指定1表示升序排序,指定-1表示降序排序。

{
   input: <array-of-documents>,
   sortBy: { sort-direction> }
}

Considerations注意事项

  • There is no implicit array traversal on the sort key.排序键上没有隐式数组遍历。
  • Positional operators are not supported. 不支持位置运算符。A field name like "values.1" denotes a sub-field called "1" in the values array. 类似“values.1”的字段名表示values数组中名为“1”的子字段。It does not refer to the item at index 1 in the values array.它不引用values数组中索引1处的项。
  • When a whole array is sorted, the sort is lexicographic. 当对整个数组进行排序时,排序是字典式的。The aggregation $sort stage, behaves differently. 聚合<$sort阶段的行为有所不同。See $sort for more details.有关详细信息,请参阅$sort
  • When an array is sorted by a field, any documents or scalars that do not have the specified field are sorted equally. 当数组按字段排序时,任何没有指定字段的文档或标量都会被同等排序。The resulting sort order is undefined.结果排序顺序未定义。
  • null values and missing values sort equally.值和缺失值的排序相同。

Sort Stability分拣稳定性

The stability of the sort is not specified. Users should not rely on $sortArray to use a particular sorting algorithm.未指定排序的稳定性。用户不应该依赖$sortArray来使用特定的排序算法。

Example示例

Create the team collection:创建team集合:

db.engineers.insertOne(
   {
      "team":
         [
            {
              "name": "pat",
              "age": 30,
              "address": { "street": "12 Baker St", "city": "London" }
            },
            {
              "name": "dallas",
              "age": 36,
              "address": { "street": "12 Cowper St", "city": "Palo Alto" }
            },
            {
              "name": "charlie",
              "age": 42,
              "address": { "street": "12 French St", "city": "New Brunswick" }
            }
         ]
   }
)

The team array has three elements. team数组有三个元素。Each element of team has nested sub-elements: name, age, and address. team的每个元素都有嵌套的子元素:nameageaddressThe following examples show how to sort the team array using these sub-elements.以下示例显示了如何使用这些子元素对team数组进行排序。

Sort on a Field按字段排序

Sort on a field within an array element:按数组元素中的字段排序:

db.engineers.aggregate( [
   { $project:
      {
          _id: 0,
          result:
            {
               $sortArray: { input: "$team", sortBy: { name: 1 } }
            }
      }
   }
] )

The name field is a sub-element in the team array. name字段是team数组中的子元素。The operation returns the following results:该操作返回以下结果:

{
   result:
   [
      {
        name: 'charlie',
        age: 42,
        address: { street: '12 French St', city: 'New Brunswick' }
      },
      {
        name: 'dallas',
        age: 36,
        address: { street: '12 Cowper St', city: 'Palo Alto' }
      },
      {
        name: 'pat',
        age: 30,
        address: { street: '12 Baker St', city: 'London' }
      }
   ]
}

Sort on a Subfield按子字段排序

The address field is a document with subfields of its own. address字段是一个具有自己的子字段的文档。Use dot notation to sort the array based on a subfield:使用点表示法根据子字段对数组进行排序:

db.engineers.aggregate( [
   {
      $project:
         {
                _id: 0,
                result:
               {
                  $sortArray:
                     {
                        input: "$team",
                        sortBy: { "address.city": -1 }
                     }
               }
             }
   }
] )

The sort direction is descending because the sortBy value is "-1".排序方向为降序,因为sortBy值为“-1”。

{
  result: [
    {
      name: 'dallas',
      age: 36,
      address: { street: '12 Cowper St', city: 'Palo Alto' }
    },
    {
      name: 'charlie',
      age: 42,
      address: { street: '12 French St', city: 'New Brunswick' }
    },
    {
      name: 'pat',
      age: 30,
      address: { street: '12 Baker St', city: 'London' }
    }
  ]
}

Sort on Multiple Fields按多个字段排序

Specify multiple index fields to do a compound sort:指定多个索引字段以进行复合排序:

db.engineers.aggregate( [
   {
      $project:
         {
            _id: 0,
            result:
               {
                  $sortArray:
                     {
                        input: "$team",
                        sortBy: { age: -1, name: 1 }
                     }
               }
         }
    }
 ] )

Example output:示例输出:

{
  name: 'charlie',
  age: 42,
  address: { street: '12 French St', city: 'New Brunswick' }
},
{
  name: 'dallas',
  age: 36,
  address: { street: '12 Cowper St', city: 'Palo Alto' }
},
{
  name: 'pat',
  age: 30,
  address: { street: '12 Baker St', city: 'London' }
}

Sort an Array of Integers对整数数组排序

This example specifies an input array directly. 此示例直接指定输入数组。The values are all the same type, Int32:这些值都是相同的类型,Int32:

db.engineers.aggregate( [
   {
      $project:
         {
            _id: 0,
            result:
               {
                  $sortArray:
                     {
                         input: [ 1, 4, 1, 6, 12, 5 ],
                         sortBy: 1
                     }
               }
         }
   }
] )

Example output:示例输出:

[ { result: [ 1, 1, 4, 5, 6, 12 ] } ]

The input array has a "1" in position 0 and position 2. 输入数组在位置0和位置2有一个“1”。The ones are grouped together in the results, but their are no guarantees regarding how the group of ones is sorted relative to their original order.它们在结果中被分组在一起,但它们不能保证一组元素是如何相对于它们的原始顺序进行排序的。

Sort on Mixed Type Fields按混合类型字段排序

This example specifies an input array directly. 此示例直接指定输入数组。The values have different types:这些值有不同的类型:

db.engineers.aggregate( [
   {
      $project:
         {
            _id: 0,
            result:
            {
               $sortArray:
                  {
                     input: [ 20, 4, { a: "Free" }, 6, 21, 5, "Gratis",
                             { a: null }, { a: { sale: true, price: 19 } },
                             Decimal128( "10.23" ), { a: "On sale" } ],
                     sortBy: 1
                  }
            }
         }
   }
] )

Example output:示例输出:

{ result: [
      4,
      5,
      6,
      Decimal128("10.23"),
      20,
      21,
      'Gratis',
      { a: null },
      { a: 'Free' },
      { a: 'On sale' },
      { a: { sale: true, price: 19 } }
] }

The results are ordered.结果是有序的。

In contrast, after changing the sortBy field to sort on the one of the document fields, sortBy: { a: 1 }, the sort order for the scalar and null values is undefined:相反,在将sortBy字段更改为在其中一个文档字段sortBy: { a: 1}上排序后,标量值和null值的排序顺序未定义:

{ result: [
     20,
     4,
     6,
     21,
     5,
     'Gratis',
     { a: null },
     Decimal128("10.23"),
     { a: 'Free' },
     { a: 'On sale' },
     { a: { sale: true, price: 19 } }
] }
←  $slice (aggregation)$split (aggregation) →