“文档” 菜单
文档首页
/
MongoDB Manual
/ / /

$sortArray(聚合)

在此页面上

  • 定义
  • 行为
  • 举例
$sortArray

5.2 版本中的新增功能

根据数组的元素对数组排序。排序顺序由用户指定。

$sortArray 通过以下语法实现:

$sortArray: {
input: <array>,
sortBy: <sort spec>
}
字段
类型
说明
input
表达式(expression)

待排序的数组。

如果表达式存在以下情况,则结果为 null

  • 缺失

  • 计算结果为 null

  • 计算结果为 undefined

如果表达式求值为任何其他非数组值,则文档将返回错误。

sortBy
文档
文档指定了排序顺序。

$sortArray 表达式根据 sortBy 规范对 input 数组进行排序。

$sortArray语法和语义与经 $sort 修改的 $push操作中的行为相同

如果数组元素为文档,则可按文档字段排序。指定字段名称和排序方向:升序 (1) 或降序 (-1)。

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

要按值或按非文档的数组元素对整个数组排序,请标识输入数组并在 sortBy 参数中指定 1(升序)或 -1(降序)。

{
input: <array-of-documents>,
sortBy: <sort-direction>
}
  • 不会对排序键进行隐式数组遍历。

  • 不支持位置操作符。像 "values.1" 这样的字段名表示 values 数组中名为 "1" 的子字段。它不引用 values 数组中索引 1 处的项目。

  • 对整个数组进行排序时,排序方式为词典排序。聚合 $sort 阶段的行为有所不同。请参阅 $sort 以了解更多详情。

  • 按字段对数组排序时,不含指定字段的文档和标量都将被平等排序。形成的排序顺序未定义。

  • null 值和缺失值的排序方式相同。

未指定排序的稳定性。用户不应依赖 $sortArray 来使用特定的排序算法。

本节中的 $sortArray 示例适用于 MongoDB 5.2 及更高版本。

创建 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" }
}
]
}
)

team 数组有三个元素。team 的每个元素都有嵌套子元素:nameageaddress。以下示例展示如何使用这些子元素对 team 数组排序。

对数组元素中的字段排序:

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

name 字段是 team 数组中的一个子元素。该操作返回以下结果:

{
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' }
}
]
}

address 字段是具有自己的子字段的文档。使用点符号根据子字段对数组进行排序:

db.engineers.aggregate( [
{
$project:
{
_id: 0,
result:
{
$sortArray:
{
input: "$team",
sortBy: { "address.city": -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' }
}
]
}

指定多个索引字段进行复合排序:

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

示例输出:

{
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' }
}

此示例直接指定输入数组。值的类型相同,都是 Int32:

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

示例输出:

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

输入数组的位置 0 和位置 2 为“1”。这些值在结果中分组在一起,但不能保证这一组值如何相对于其原始顺序进行排序。

此示例将直接指定输入数组。这些值具有不同类型:

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
}
}
}
}
] )

示例输出:

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

结果已进行排序。

在更改 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(聚合)

来年

$split(聚合)

在此页面上