DolphinDB时间序列引擎:实时聚合计算

目录

    • 摘要
    • 一、时间序列引擎概述
      • [1.1 什么是时间序列引擎](#1.1 什么是时间序列引擎)
      • [1.2 时间序列引擎特点](#1.2 时间序列引擎特点)
      • [1.3 适用场景](#1.3 适用场景)
    • 二、创建时间序列引擎
      • [2.1 基本语法](#2.1 基本语法)
      • [2.2 创建简单引擎](#2.2 创建简单引擎)
      • [2.3 创建分组引擎](#2.3 创建分组引擎)
    • 三、窗口类型
      • [3.1 固定窗口](#3.1 固定窗口)
      • [3.2 滑动窗口](#3.2 滑动窗口)
      • [3.3 时间对齐](#3.3 时间对齐)
    • 四、聚合指标
      • [4.1 基本聚合](#4.1 基本聚合)
      • [4.2 百分位聚合](#4.2 百分位聚合)
      • [4.3 自定义聚合](#4.3 自定义聚合)
      • [4.4 多列聚合](#4.4 多列聚合)
    • 五、引擎管理
      • [5.1 查看引擎状态](#5.1 查看引擎状态)
      • [5.2 删除引擎](#5.2 删除引擎)
      • [5.3 引擎监控](#5.3 引擎监控)
    • 六、实战案例
      • [6.1 设备实时监控](#6.1 设备实时监控)
      • [6.2 实时告警系统](#6.2 实时告警系统)
      • [6.3 数据降采样](#6.3 数据降采样)
    • 七、性能优化
      • [7.1 窗口大小选择](#7.1 窗口大小选择)
      • [7.2 分组数量](#7.2 分组数量)
      • [7.3 内存管理](#7.3 内存管理)
    • 八、总结
    • 参考资料

摘要

本文深入讲解DolphinDB时间序列引擎。从引擎原理到创建配置,从窗口聚合到滑动计算,从多设备分组到实时输出,全面介绍时间序列引擎的核心功能。通过丰富的代码示例,帮助读者掌握实时聚合计算的核心技能。


一、时间序列引擎概述

1.1 什么是时间序列引擎

时间序列引擎是DolphinDB内置的流计算引擎,用于实时时间窗口聚合:
时间序列引擎
数据流
时间窗口
窗口聚合
实时输出
核心功能
固定窗口
滑动窗口
会话窗口

1.2 时间序列引擎特点

特点 说明
实时聚合 毫秒级延迟
窗口计算 支持多种窗口
分组聚合 支持多设备分组
自动触发 窗口结束自动输出

1.3 适用场景

场景 说明
实时监控 设备指标实时统计
告警检测 实时阈值告警
趋势分析 实时趋势计算
数据降采样 高频数据降采样

二、创建时间序列引擎

2.1 基本语法

python 复制代码
// 创建时间序列引擎
agg = createTimeSeriesEngine(
    "engine_name",     // 引擎名称
    windowSize,        // 窗口大小(毫秒)
    metrics,           // 聚合指标
    outputTable,       // 输出表
    timeColumn,        // 时间列
    [keyColumn],       // 分组列(可选)
    [garbageSize],     // 垃圾回收阈值
    [roundTime]        // 时间对齐方式
)

2.2 创建简单引擎

python 复制代码
// 创建输入流表
share streamTable(1:0, 
    `timestamp`temperature,
    [TIMESTAMP, DOUBLE]) as input_stream

// 创建输出表
share table(1:0,
    `timestamp`avg_temp`max_temp`min_temp`cnt,
    [TIMESTAMP, DOUBLE, DOUBLE, DOUBLE, LONG]) as output_table

// 创建时间序列引擎
agg = createTimeSeriesEngine("ts_engine", 60000,  // 60秒窗口
    <[avg(temperature) as avg_temp,
      max(temperature) as max_temp,
      min(temperature) as min_temp,
      count(temperature) as cnt]>,
    output_table, `timestamp)

// 订阅流表
subscribeTable(, "input_stream", "ts_agg", -1, agg, true)

2.3 创建分组引擎

python 复制代码
// 创建输入流表
share streamTable(1:0, 
    `device_id`timestamp`temperature,
    [INT, TIMESTAMP, DOUBLE]) as input_stream

// 创建输出表
share table(1:0,
    `device_id`timestamp`avg_temp`max_temp`min_temp`cnt,
    [INT, TIMESTAMP, DOUBLE, DOUBLE, DOUBLE, LONG]) as output_table

// 创建分组时间序列引擎
agg = createTimeSeriesEngine("grouped_ts_engine", 60000,
    <[avg(temperature) as avg_temp,
      max(temperature) as max_temp,
      min(temperature) as min_temp,
      count(temperature) as cnt]>,
    output_table, `timestamp, `device_id)

// 订阅流表
subscribeTable(, "input_stream", "grouped_ts_agg", -1, agg, true)

三、窗口类型

3.1 固定窗口

python 复制代码
// 固定窗口:窗口大小固定,不重叠
// 例如:每60秒一个窗口

agg = createTimeSeriesEngine("fixed_window", 60000,
    <[avg(temperature) as avg_temp,
      count(*) as cnt]>,
    output_table, `timestamp, `device_id)

// 窗口划分:
// [00:00:00, 00:01:00) -> 窗口1
// [00:01:00, 00:02:00) -> 窗口2
// [00:02:00, 00:03:00) -> 窗口3

3.2 滑动窗口

python 复制代码
// 滑动窗口:窗口按步长滑动
// 使用createTimeSeriesEngine的step参数

agg = createTimeSeriesEngine("sliding_window", 
    60000,  // 窗口大小60秒
    <[avg(temperature) as avg_temp]>,
    output_table, `timestamp, `device_id,
    , , , 10000)  // step=10秒

// 窗口划分(每10秒输出一次):
// [00:00:00, 00:01:00) -> 00:01:00输出
// [00:00:10, 00:01:10) -> 00:01:10输出
// [00:00:20, 00:01:20) -> 00:01:20输出

3.3 时间对齐

python 复制代码
// 时间对齐:窗口边界对齐到整点时间
agg = createTimeSeriesEngine("aligned_window", 60000,
    <[avg(temperature) as avg_temp]>,
    output_table, `timestamp, `device_id,
    , , true)  // roundTime=true,时间对齐

// 对齐效果:
// 数据时间 00:00:30 -> 窗口 [00:00:00, 00:01:00)
// 数据时间 00:01:15 -> 窗口 [00:01:00, 00:02:00)

四、聚合指标

4.1 基本聚合

python 复制代码
// 基本聚合函数
agg = createTimeSeriesEngine("basic_agg", 60000,
    <[avg(temperature) as avg_temp,      // 平均值
      sum(temperature) as sum_temp,      // 总和
      max(temperature) as max_temp,      // 最大值
      min(temperature) as min_temp,      // 最小值
      count(temperature) as cnt,         // 计数
      std(temperature) as std_temp,      // 标准差
      var(temperature) as var_temp]>,    // 方差
    output_table, `timestamp, `device_id)

4.2 百分位聚合

python 复制代码
// 百分位聚合
agg = createTimeSeriesEngine("percentile_agg", 60000,
    <[percentile(temperature, 50) as median,  // 中位数
      percentile(temperature, 95) as p95,     // 95分位
      percentile(temperature, 99) as p99]>,   // 99分位
    output_table, `timestamp, `device_id)

4.3 自定义聚合

python 复制代码
// 自定义聚合指标
agg = createTimeSeriesEngine("custom_agg", 60000,
    <[avg(temperature) as avg_temp,
      max(temperature) - min(temperature) as range,  // 极差
      std(temperature) / avg(temperature) as cv]>,   // 变异系数
    output_table, `timestamp, `device_id)

4.4 多列聚合

python 复制代码
// 多列聚合
agg = createTimeSeriesEngine("multi_col_agg", 60000,
    <[avg(temperature) as avg_temp,
      avg(humidity) as avg_humidity,
      avg(pressure) as avg_pressure,
      corr(temperature, humidity) as corr_temp_humid]>,
    output_table, `timestamp, `device_id)

五、引擎管理

5.1 查看引擎状态

python 复制代码
// 查看引擎状态
getStreamEngineStat()

// 查看特定引擎
getStreamEngineStat("ts_engine")

5.2 删除引擎

python 复制代码
// 删除引擎
dropStreamEngine("ts_engine")

// 删除所有引擎
dropStreamEngine()

5.3 引擎监控

python 复制代码
// 引擎监控函数
def monitorEngine() {
    stat = getStreamEngineStat()
    for (row in stat) {
        print("引擎: " + row.name)
        print("  状态: " + row.status)
        print("  处理行数: " + string(row.processedRows))
        print("  输出行数: " + string(row.outputRows))
    }
}

monitorEngine()

六、实战案例

6.1 设备实时监控

python 复制代码
// ========== 1. 创建流表 ==========
share streamTable(100000:0, 
    `device_id`timestamp`temperature`humidity`pressure,
    [INT, TIMESTAMP, DOUBLE, DOUBLE, DOUBLE]) as sensor_stream

// ========== 2. 创建输出表 ==========
share table(1:0,
    `device_id`timestamp`avg_temp`max_temp`min_temp`avg_humidity`cnt,
    [INT, TIMESTAMP, DOUBLE, DOUBLE, DOUBLE, DOUBLE, LONG]) as monitor_result

// ========== 3. 创建时间序列引擎 ==========
agg = createTimeSeriesEngine("monitor_engine", 60000,  // 1分钟窗口
    <[avg(temperature) as avg_temp,
      max(temperature) as max_temp,
      min(temperature) as min_temp,
      avg(humidity) as avg_humidity,
      count(*) as cnt]>,
    monitor_result, `timestamp, `device_id)

// ========== 4. 订阅流表 ==========
subscribeTable(, "sensor_stream", "monitor_agg", -1, agg, true)

// ========== 5. 启用持久化 ==========
enableTablePersistence(sensor_stream, true, true, 1000000)

// ========== 6. 模拟数据写入 ==========
def simulateData() {
    for (i in 1..100) {
        sensor_stream.append!(
            table(
                take(1..100, 1000) as device_id,
                take(now(), 1000) as timestamp,
                rand(20.0..30.0, 1000) as temperature,
                rand(40.0..60.0, 1000) as humidity,
                rand(1000.0..1020.0, 1000) as pressure
            )
        )
        sleep(100)
    }
}

// 执行模拟
simulateData()

// 查看结果
select top 20 * from monitor_result

6.2 实时告警系统

python 复制代码
// ========== 1. 创建流表 ==========
share streamTable(100000:0, 
    `device_id`timestamp`temperature,
    [INT, TIMESTAMP, DOUBLE]) as sensor_stream

// ========== 2. 创建输出表 ==========
share table(1:0,
    `device_id`timestamp`avg_temp`alert,
    [INT, TIMESTAMP, DOUBLE, BOOL]) as alert_result

// ========== 3. 创建告警引擎 ==========
agg = createTimeSeriesEngine("alert_engine", 30000,  // 30秒窗口
    <[avg(temperature) as avg_temp,
      avg(temperature) > 30 as alert]>,  // 温度>30告警
    alert_result, `timestamp, `device_id)

// ========== 4. 订阅流表 ==========
subscribeTable(, "sensor_stream", "alert_agg", -1, agg, true)

// ========== 5. 查询告警 ==========
select * from alert_result where alert = true

6.3 数据降采样

python 复制代码
// ========== 1. 创建高频数据流表 ==========
share streamTable(100000:0, 
    `device_id`timestamp`value,
    [INT, TIMESTAMP, DOUBLE]) as high_freq_stream

// ========== 2. 创建降采样输出表 ==========
share table(1:0,
    `device_id`timestamp`open`high`low`close`cnt,
    [INT, TIMESTAMP, DOUBLE, DOUBLE, DOUBLE, DOUBLE, LONG]) as ohlc_result

// ========== 3. 创建降采样引擎 ==========
agg = createTimeSeriesEngine("ohlc_engine", 60000,  // 1分钟降采样
    <[first(value) as open,    // 开盘
      max(value) as high,      // 最高
      min(value) as low,       // 最低
      last(value) as close,    // 收盘
      count(*) as cnt]>,       // 数量
    ohlc_result, `timestamp, `device_id)

// ========== 4. 订阅流表 ==========
subscribeTable(, "high_freq_stream", "ohlc_agg", -1, agg, true)

七、性能优化

7.1 窗口大小选择

场景 建议窗口大小
实时监控 10-60秒
告警检测 30-60秒
趋势分析 1-5分钟
数据降采样 1-10分钟

7.2 分组数量

python 复制代码
// 分组数量建议
// 单引擎分组数 < 10000

// 如果分组数过多,考虑:
// 1. 使用多个引擎
// 2. 使用哈希分组

7.3 内存管理

python 复制代码
// 设置垃圾回收阈值
agg = createTimeSeriesEngine("ts_engine", 60000,
    <[avg(temperature) as avg_temp]>,
    output_table, `timestamp, `device_id,
    100000)  // garbageSize=100000,超过10万条触发GC

八、总结

本文详细介绍了DolphinDB时间序列引擎:

  1. 引擎原理:实时时间窗口聚合
  2. 创建方法:简单引擎、分组引擎
  3. 窗口类型:固定窗口、滑动窗口、时间对齐
  4. 聚合指标:基本聚合、百分位、自定义
  5. 引擎管理:状态查看、删除、监控
  6. 实战应用:实时监控、告警系统、数据降采样

思考题

  1. 如何选择合适的窗口大小?
  2. 固定窗口和滑动窗口有什么区别?
  3. 如何设计实时告警系统?

参考资料

相关推荐
阿黎梨梨4 小时前
跟 Git 打交道的正确姿势
前端
idcu4 小时前
深入 Lyt.js 路由系统:L6 生态系统层的核心
前端·typescript
idcu4 小时前
用 Lyt.js 构建 Todo 应用:完整教程
前端·typescript
佳木逢钺4 小时前
pnpm 命令功能清单
前端
木雷坞4 小时前
Home Assistant Docker Compose 升级失败排查:镜像、备份和设备映射
服务器·docker·home assisant
m0_738120724 小时前
渗透测试基础知识——从零认识JWT(JSON Web Token)身份令牌
服务器·前端·安全·web安全·网络安全·json
放下华子我只抽RuiKe54 小时前
React 从入门到生产(六):路由与导航
前端·人工智能·深度学习·react.js·前端框架·html·claude code
Sylus_sui4 小时前
实现:每行固定 5 个、自动换行、最后一行左对齐、数量不固定
前端·javascript·css
文滨4 小时前
10分钟搞定!Mac 配置 GitHub SSH 完全指南(小白也能看懂)
前端·macos·ssh·github