$derivative
聚合运算符返回返回指定窗口内的平均变化率(即求导),变化率使用以下公式计算:
$setWindowFields
阶段窗口中的第一个和最后一个文件。- 分子,等于最后一个文档的表达式的值减去第一个文档表达式的值。
- 分母,等于最后一个文档
sortBy
字段值减去第一个文档sortBy
字段值。
语法
js
{
$derivative: {
input: <expression>,
unit: <time unit>
}
}
参数说明:
<expression>
指定要指定的表达式,表达式必须要能被解析为数值unit
字符串,用于指定时间单位,可以是:week
、day
、hour
、minute
、second
、millisecond
。如果sortBy
字段不是日期类型,就必须忽略unit
,换而言之,如果指定了unit
,那么sortBy
就必须是日期类型字段。
使用
$derivative
只能用于$setWindowFields
阶段,而且必须指定一个窗口。
举例
使用下面的脚本创建deliveryFleet
集合,其内容是以30秒为间隔的送货卡车的里程表读数:
js
db.deliveryFleet.insertMany( [
{ truckID: "1", timeStamp: new Date( "2020-05-18T14:10:30Z" ), miles: 1295.1 },
{ truckID: "1", timeStamp: new Date( "2020-05-18T14:11:00Z" ), miles: 1295.63 },
{ truckID: "1", timeStamp: new Date( "2020-05-18T14:11:30Z" ), miles: 1296.25 },
{ truckID: "1", timeStamp: new Date( "2020-05-18T14:12:00Z" ), miles: 1296.76 },
{ truckID: "2", timeStamp: new Date( "2020-05-18T14:10:30Z" ), miles: 10234.1 },
{ truckID: "2", timeStamp: new Date( "2020-05-18T14:11:00Z" ), miles: 10234.33 },
{ truckID: "2", timeStamp: new Date( "2020-05-18T14:11:30Z" ), miles: 10234.73 },
{ truckID: "2", timeStamp: new Date( "2020-05-18T14:12:00Z" ), miles: 10235.13 }
] )
本例在$setWindowFields
阶段使用$derivative
获得每辆卡车的平均车速,单位是英里/小时,并且使用$match
阶段过滤掉车速小于50英里/每小时的卡车。
js
db.deliveryFleet.aggregate( [
{
$setWindowFields: {
partitionBy: "$truckID",
sortBy: { timeStamp: 1 },
output: {
truckAverageSpeed: {
$derivative: {
input: "$miles",
unit: "hour"
},
window: {
range: [ -30, 0 ],
unit: "second"
}
}
}
}
},
{
$match: {
truckAverageSpeed: {
$gt: 50
}
}
}
] )
在本例中:
$setWindowFields
阶段获取每辆卡车每小时英里数的平均车速:partitionBy: "$truckID"
根据truckID
对集合文档进行分区sortBy:{timeStamp:1}
根据timeStamp
字段对文档进行正向排序,最早的里程表读数排在最前面output
在窗口范围内使用$derivative
将mailes
的导数值赋予新的字段truckAverageSpeed
。input
表达式为$miles
,作为求导计算的分子$derivative
为timeStamp
字段指定了"hour"
为单位,作为求导计算的分母- 窗口包含了下限-30秒(前30秒的文档)和0秒(当前文档的时间戳)之间的范围。这意味着
$derivative
返回卡车在30秒窗口中的速度(英里/小时)。
$match
阶段使用大于运算符$gt
筛选出平均速度大于50英里每小时的卡车。
在下面的输出中可以看出,卡车1的速度显示在truckAverageSpeed
字段,卡车2的速度没有显示,因为卡车2的速度未超过50英里每小时
json
{ "_id" : ObjectId("60cb8a7e833dfeadc8e6285c"), "truckID" : "1",
"timeStamp" : ISODate("2020-05-18T14:11:00Z"), "miles" : 1295.63,
"truckAverageSpeed" : 63.60000000002401 }
{ "_id" : ObjectId("60cb8a7e833dfeadc8e6285d"), "truckID" : "1",
"timeStamp" : ISODate("2020-05-18T14:11:30Z"), "miles" : 1296.25,
"truckAverageSpeed" : 74.3999999999869 }
{ "_id" : ObjectId("60cb8a7e833dfeadc8e6285e"), "truckID" : "1",
"timeStamp" : ISODate("2020-05-18T14:12:00Z"), "miles" : 1296.76,
"truckAverageSpeed" : 61.199999999998916 }