Compute a single aggregate over a group of msgpack rows.
(op: &str, field: &str, rows: &[&[u8]])
| 194 | |
| 195 | /// Compute a single aggregate over a group of msgpack rows. |
| 196 | fn compute_aggregate(op: &str, field: &str, rows: &[&[u8]]) -> AggValue { |
| 197 | match op { |
| 198 | "count" => AggValue::Int(rows.len() as i64), |
| 199 | "sum" => { |
| 200 | let sum: f64 = rows.iter().filter_map(|r| extract_number(r, field)).sum(); |
| 201 | AggValue::Float(sum) |
| 202 | } |
| 203 | "avg" => { |
| 204 | let values: Vec<f64> = rows |
| 205 | .iter() |
| 206 | .filter_map(|r| extract_number(r, field)) |
| 207 | .collect(); |
| 208 | if values.is_empty() { |
| 209 | AggValue::Null |
| 210 | } else { |
| 211 | AggValue::Float(values.iter().sum::<f64>() / values.len() as f64) |
| 212 | } |
| 213 | } |
| 214 | "min" => rows |
| 215 | .iter() |
| 216 | .filter_map(|r| extract_number(r, field)) |
| 217 | .min_by(|a, b| a.partial_cmp(b).unwrap_or(std::cmp::Ordering::Equal)) |
| 218 | .map(AggValue::Float) |
| 219 | .unwrap_or(AggValue::Null), |
| 220 | "max" => rows |
| 221 | .iter() |
| 222 | .filter_map(|r| extract_number(r, field)) |
| 223 | .max_by(|a, b| a.partial_cmp(b).unwrap_or(std::cmp::Ordering::Equal)) |
| 224 | .map(AggValue::Float) |
| 225 | .unwrap_or(AggValue::Null), |
| 226 | _ => AggValue::Null, |
| 227 | } |
| 228 | } |
no test coverage detected