Services or capabilities described in Amazon Web Services documentation might vary by Region. To see the differences applicable to the China Regions,
see Getting Started with Amazon Web Services in China
(PDF).
$stdDevSamp
New from version 8.0.1.
The $stdDevSamp operator in Amazon DocumentDB calculates the sample standard deviation of numeric values. As an accumulator, it computes the sample standard deviation across documents within a group in the $group stage of an aggregation pipeline. As an expression, it calculates the sample standard deviation of an array of numbers. The sample standard deviation uses N-1 as the divisor (Bessel's correction). Non-numeric values are ignored. If there are fewer than two numeric values, it returns null.
Parameters
Example (MongoDB Shell)
The following example shows how to use the $stdDevSamp operator to calculate the sample standard deviation of scores per subject.
Create sample documents
db.scores.insertMany([
{ subject: "math", score: 80 },
{ subject: "math", score: 90 },
{ subject: "math", score: 85 },
{ subject: "math", score: 95 },
{ subject: "science", score: 70 },
{ subject: "science", score: 75 },
{ subject: "science", score: 80 },
{ subject: "science", score: 85 }
]);
Query example
db.scores.aggregate([
{ $group: {
_id: "$subject",
stdDev: { $stdDevSamp: "$score" }
}}
]);
Output
[
{ "_id": "math", "stdDev": 6.454972243679028 },
{ "_id": "science", "stdDev": 6.454972243679028 }
]
Expression usage example (MongoDB Shell)
The $stdDevSamp operator can also be used as an expression within a $project stage to compute the sample standard deviation of an array field.
Create sample documents
db.experiments.insertMany([
{ _id: 1, measurements: [10, 12, 14, 16, 18] },
{ _id: 2, measurements: [5, 5, 5, 5, 5] },
{ _id: 3, measurements: [2, 4, 6, 8, 10] }
]);
Query example
db.experiments.aggregate([
{ $project: {
stdDev: { $stdDevSamp: "$measurements" }
}}
]);
Output
[
{ "_id": 1, "stdDev": 3.1622776601683795 },
{ "_id": 2, "stdDev": 0 },
{ "_id": 3, "stdDev": 3.1622776601683795 }
]
Window operator usage example (MongoDB Shell)
New from version 8.0.2.
The $stdDevSamp operator can also be used as a window operator in the $setWindowFields stage. In this context, it returns the sample standard deviation of the specified expression for the documents in each window. You specify the operator under the output field, and optionally define the window boundaries with a window document.
Create sample documents
db.sensorReadings.insertMany([
{ _id: 1, sensor: "A", time: 1, value: 2 },
{ _id: 2, sensor: "A", time: 2, value: 4 },
{ _id: 3, sensor: "A", time: 3, value: 6 },
{ _id: 4, sensor: "B", time: 1, value: 10 },
{ _id: 5, sensor: "B", time: 2, value: 12 }
]);
Query example
The following example partitions the documents by sensor, sorts each partition by time, and returns the running sample standard deviation of value from the start of the partition through the current document.
db.sensorReadings.aggregate([
{
$setWindowFields: {
partitionBy: "$sensor",
sortBy: { time: 1 },
output: {
runningStdDev: {
$stdDevSamp: "$value",
window: { documents: ["unbounded", "current"] }
}
}
}
}
]);
Output
[
{ "_id": 1, "sensor": "A", "time": 1, "value": 2, "runningStdDev": null },
{ "_id": 2, "sensor": "A", "time": 2, "value": 4, "runningStdDev": 1.4142135623730951 },
{ "_id": 3, "sensor": "A", "time": 3, "value": 6, "runningStdDev": 2 },
{ "_id": 4, "sensor": "B", "time": 1, "value": 10, "runningStdDev": null },
{ "_id": 5, "sensor": "B", "time": 2, "value": 12, "runningStdDev": 1.4142135623730951 }
]
Each document is augmented with runningStdDev, the sample standard deviation of value within its partition up to and including the current document. When the window contains fewer than two values (the first document in each partition), $stdDevSamp returns null.
Code examples
To view a code example for using the $stdDevSamp operator, choose the tab for the language that you want to use. The following examples show accumulator usage (in $group), expression usage (in $project), and window operator usage (in $setWindowFields):
- Node.js
-
const { MongoClient } = require('mongodb');
async function example() {
const uri = 'mongodb://<username>:<password>@<cluster-endpoint>:27017/?tls=true&tlsCAFile=global-bundle.pem&replicaSet=rs0&readPreference=secondaryPreferred&retryWrites=false';
const client = new MongoClient(uri);
try {
await client.connect();
const db = client.db('test');
// Accumulator usage: stdDevSamp across grouped documents
const scores = db.collection('scores');
await scores.insertMany([
{ subject: "math", score: 80 },
{ subject: "math", score: 90 },
{ subject: "math", score: 85 },
{ subject: "math", score: 95 },
{ subject: "science", score: 70 },
{ subject: "science", score: 75 },
{ subject: "science", score: 80 },
{ subject: "science", score: 85 }
]);
const accumulatorResult = await scores.aggregate([
{ $group: {
_id: "$subject",
stdDev: { $stdDevSamp: "$score" }
}}
]).toArray();
console.log('Accumulator result:', accumulatorResult);
// Expression usage: stdDevSamp of an array field
const experiments = db.collection('experiments');
await experiments.insertMany([
{ _id: 1, measurements: [10, 12, 14, 16, 18] },
{ _id: 2, measurements: [5, 5, 5, 5, 5] },
{ _id: 3, measurements: [2, 4, 6, 8, 10] }
]);
const expressionResult = await experiments.aggregate([
{ $project: {
stdDev: { $stdDevSamp: "$measurements" }
}}
]).toArray();
console.log('Expression result:', expressionResult);
// Window operator usage: running stdDevSamp within each partition
const sensorReadings = db.collection('sensorReadings');
await sensorReadings.insertMany([
{ _id: 1, sensor: "A", time: 1, value: 2 },
{ _id: 2, sensor: "A", time: 2, value: 4 },
{ _id: 3, sensor: "A", time: 3, value: 6 },
{ _id: 4, sensor: "B", time: 1, value: 10 },
{ _id: 5, sensor: "B", time: 2, value: 12 }
]);
const windowResult = await sensorReadings.aggregate([
{
$setWindowFields: {
partitionBy: "$sensor",
sortBy: { time: 1 },
output: {
runningStdDev: {
$stdDevSamp: "$value",
window: { documents: ["unbounded", "current"] }
}
}
}
}
]).toArray();
console.log('Window result:', windowResult);
} finally {
await client.close();
}
}
example();
- Python
-
from pymongo import MongoClient
def example():
client = MongoClient('mongodb://<username>:<password>@<cluster-endpoint>:27017/?tls=true&tlsCAFile=global-bundle.pem&replicaSet=rs0&readPreference=secondaryPreferred&retryWrites=false')
try:
db = client['test']
# Accumulator usage: stdDevSamp across grouped documents
scores = db['scores']
scores.insert_many([
{ 'subject': 'math', 'score': 80 },
{ 'subject': 'math', 'score': 90 },
{ 'subject': 'math', 'score': 85 },
{ 'subject': 'math', 'score': 95 },
{ 'subject': 'science', 'score': 70 },
{ 'subject': 'science', 'score': 75 },
{ 'subject': 'science', 'score': 80 },
{ 'subject': 'science', 'score': 85 }
])
accumulator_result = list(scores.aggregate([
{ '$group': {
'_id': '$subject',
'stdDev': { '$stdDevSamp': '$score' }
}}
]))
print('Accumulator result:', accumulator_result)
# Expression usage: stdDevSamp of an array field
experiments = db['experiments']
experiments.insert_many([
{ '_id': 1, 'measurements': [10, 12, 14, 16, 18] },
{ '_id': 2, 'measurements': [5, 5, 5, 5, 5] },
{ '_id': 3, 'measurements': [2, 4, 6, 8, 10] }
])
expression_result = list(experiments.aggregate([
{ '$project': {
'stdDev': { '$stdDevSamp': '$measurements' }
}}
]))
print('Expression result:', expression_result)
# Window operator usage: running stdDevSamp within each partition
sensor_readings = db['sensorReadings']
sensor_readings.insert_many([
{ '_id': 1, 'sensor': 'A', 'time': 1, 'value': 2 },
{ '_id': 2, 'sensor': 'A', 'time': 2, 'value': 4 },
{ '_id': 3, 'sensor': 'A', 'time': 3, 'value': 6 },
{ '_id': 4, 'sensor': 'B', 'time': 1, 'value': 10 },
{ '_id': 5, 'sensor': 'B', 'time': 2, 'value': 12 }
])
window_result = list(sensor_readings.aggregate([
{
'$setWindowFields': {
'partitionBy': '$sensor',
'sortBy': { 'time': 1 },
'output': {
'runningStdDev': {
'$stdDevSamp': '$value',
'window': { 'documents': ['unbounded', 'current'] }
}
}
}
}
]))
print('Window result:', window_result)
finally:
client.close()
example()