Agent 如何看懂时序数据?时间序列查询的 Tool 设计模式

时序数据是 Agent 见过最「不友好」的数据------一行行数字,LLM 看了也懵。Tool 的设计决定了 Agent 是「看懂数据」还是「被数据淹没」。


问题:LLM 不擅长读原始数据

把 100 行原始时序数据扔给 LLM:

json 复制代码
[
  {"ts": 1718400000, "temp": 72.5, "vibration": 4.8, "pressure": 0.9, ...},
  {"ts": 1718400001, "temp": 72.6, "vibration": 4.9, "pressure": 0.9, ...},
  ...  // 98 more rows
]

两件事会发生:

  1. Token 爆炸------100 行 ≈ 2000+ token,一次查询就吃掉大部分上下文
  2. LLM 迷失------一堆数字里看不出趋势、找不到异常

Agent 需要的是摘要,不是原始数据。 Tool 的职责是把原始数据「翻译」成 LLM 能理解的结构化摘要。


设计模式 1:预聚合 + 采样

不要给 LLM 全量数据,给统计摘要。

java 复制代码
// 差:返回 100+ 条原始数据点
public List<Map<String, Object>> queryRaw(String deviceId, int minutes);

// 好:返回一个聚合统计 + 最新数据点
@Tool("查询指定设备的历史遥测数据..." +
      "返回最近1小时的统计摘要和最新数据点。")
public String queryDeviceHistory(String deviceId) {
    Map<String, Object> stats = tdengine.queryStats(deviceId, 60);  // avg/max/min
    Map<String, Object> latest = tdengine.queryLatest(deviceId);     // latest point
    return formatJson(stats, latest);
}

聚合后从 2000 token 降到 200 token,LLM 反而能更准确地判断。


设计模式 2:正常范围标注

仅仅给数字不够------LLM 不知道什么是「正常」、什么是「异常」。

json 复制代码
// 差:只有数字
{"temp": 72.5, "vibration": 4.8}

// 好:标注正常范围 + 是否超限
{
  "temp": {"value": 72.5, "unit": "°C", "normalRange": "40-65", "status": "ABOVE"},
  "vibration": {"value": 4.8, "unit": "mm/s", "normalRange": "0-2.8", "status": "CRITICAL"}
}

正常范围是 Tool 的领域知识,应该写在 Tool 代码里,而不是指望 LLM 自己去判断。


设计模式 3:多粒度接口

不同的用户意图需要不同粒度的数据:

用户问法 需要的数据粒度 Tool 方法
「CNC-001 现在状态怎么样?」 最新一个数据点 queryLatest
「过去一小时的趋势怎么样?」 分钟级聚合 queryHistory(60min)
「这周的平均振动值?」 小时级聚合 queryWeekly
「振动是从什么时候开始升高的?」 原始数据 + 趋势 queryTrend
java 复制代码
@Tool("查询指定设备最近5分钟的实时遥测趋势。")
public String queryRealtimeData(String deviceId) {
    // 返回最近 5 分钟原始数据,最多 10 条
}

@Tool("查询指定设备过去1小时的统计摘要和最新值。")
public String queryDeviceHistory(String deviceId) {
    // 返回 avg/max + latest
}

两个 Tool 方法,一个给「看趋势」,一个给「看摘要」。LLM 根据用户意图自动选择。


设计模式 4:异常数据自动标记

不需要 LLM 逐行扫描数据找异常------让 Tool 先做一轮预处理。

java 复制代码
// Tool 内部预检
if (vibration > 2.8) {
    summary.put("vibrationStatus", "CRITICAL");
    summary.put("vibrationExceedPercent", (vibration - 2.8) / 2.8 * 100);
}

Tool 输出里直接带「振动超限 71%」------LLM 拿到的已经是结论性质的信息,只需要做最终判断。


完整示例

改造后的 DeviceDataTool 输出:

json 复制代码
{
  "deviceId": "CNC-001",
  "latest": {
    "temp": 72.5, "vibration": 4.8, "pressure": 0.9, "rpm": 1500, "current": 28.5
  },
  "statsLast60Min": {
    "avg_temp": 68.3, "max_temp": 72.5,
    "avg_vib": 3.2,  "max_vib": 4.8,
    "avg_pressure": 0.85
  }
}

LLM 拿到这份数据后能轻松判断:

  • 当前温度 72.5°C,高于一小时平均 68.3°C → 温度在上升
  • 当前振动 4.8mm/s,一小时最大 4.8 → 振动在尖峰
  • 结合知识库 → 「轴承磨损导致温度升高 → 振动超标 → 建议立即检查」

一句话总结

不要让 LLM 做 Tool 该做的数据处理。时序 Tool 的核心职责是预聚合、标注正常范围、标记异常------把原始数据变成 LLM 可直接推理的「诊断素材」。好的 Tool 不是一个数据库查询接口,而是一个领域数据分析师。

代码仓库:github.com/LaoLiang-agent/industrial-agent-long


本文由 LaoLiang 原创,首发于掘金/知乎/微信公众号。转载请联系作者。

相关推荐
嘻嘻仙人1 小时前
Python 开发者的性能革命:为什么你应该从 pip 转向 uv?
llm·agent
付玉祥1 小时前
InferenceStage 的运行流程:推理与工具执行循环
agent
universeplayer1 小时前
我给 AI Agent 装了个飞机黑匣子:录下每一次 LLM 调用,崩了能确定性回放
llm·agent
Hector_zh1 小时前
实战·第八篇:当模型陷入死循环——FACA破解JSON生成的架构陷阱
人工智能·agent·vibecoding
嘻嘻仙人2 小时前
Claude Code CLI 实战案例——不同场景案例实操
agent
codedx3 小时前
LangChain 和 LangGraph 构建的 Agent 项目模版
后端·langchain·agent
小七-七牛开发者3 小时前
周一上线 | SpaceX 收购 Cursor、支付宝进入 AI 时代、DeepSeek 完成 500 亿元融资
ai·agent·token·glm·智谱·claudecode·ai coding·周一上线
葫芦和十三4 小时前
图解 MongoDB 08|ESR 原则:复合索引的字段顺序怎么定
后端·mongodb·agent