智能问数NLQ 令准确率失去意义的
Text2SQL技术

当前技术现状

直接生成SQL的问题

语义错误很难被识别

  • 语法错误SQL语法错误,执行的时候会报错,比较容易发现
  • 语义错误SQL语义错误,执行也能得到结果,用户无法判断是否正确
缺乏可确认的控幻机制,企业无法接受这种不确定性

中间层方案的困境

DSL不可读是致命问题,即使90%正确率也无法实用,业务用户挑不出剩下10%

Text2SQL的三难困境

现有技术的不可能三角
  • 灵活性:理解多样化表达
  • 准确性:生成正确 SQL
  • 查询复杂性:支持复杂计算
核心困境:生成的 SQL 或 DSL 均无法被业务用户理解和确认

智能问数解决方案

NLQ是什么?

  • 支持人类确认的Text2SQL
  • 自然语言表达的规范文本DSL
  • 兼得灵活性/准确性/查询复杂性
  • NLQ: Natural Language Query

NLQ处理流程

  • 规范文本控幻:自然语言人类可读可确认
  • NLQ确定转换:解析规范文本准确转换MQL
  • MQL复杂支持:支持关联嵌套等全BI场景
规范文本

规范文本:人机双向可读的DSL

DSL使用规范的自然语言

自然语言
  • 出生日期在 1986 年 1 月至 7 月的雇员(前后单位不统一,后面缺少年份)
  • 订单里哪个商品打折力度最大?(使用了过于口语化的“打折力度”)
  • 去年谁没开单?( “开单”属于行业“黑话”)
规范文本
  • 出生日期在 1986 年 1 月至 1986 年 7 月的雇员
  • 订单明细,折扣 最大者,产品 名称
  • 签单日期 上个月,没有 订单,员工
LLM转换成规范文本也会有幻觉,但人类能看懂、能确认

人机双向可读

人类可确认性

规范文本采用业务人员熟悉的自然语言,使用户能够直观确认查询意图确认环节是解决幻觉问题的关键

机器可解析性

规范文本遵循预定义的结构与词汇表,具备极强的机器可解析性,为支撑复杂查询奠定了基础

规范文本的意义

  • 角色重塑LLM任务简化为文本转写,通用模型即可工作
  • 准确稳定人类可确认与引擎校验构成双重保障,确保查询意图精准无误
  • 破解困境兼顾自然语言的灵活性、规则引擎的准确性与企业级查询的复杂性
  • 部署灵活规范文本可脱离LLM由直接工作,适应API方案运行

NLQ配合LLM的确认环节

NLQ词典

NLQ引擎 – 100%准确率的保证

实现方式:NLQ词典

基于词典的规则引擎保证准确性

  • 预先建立词典,导入数据结构,定义表词、字段词、维词等
  • 利用词典解析出规范文本中的表、字段、比较符号、聚合函数等SQL要素

NLQ词典 – 基本概念

类别 说明 解释与示例
表与实体 是数据库中的物理表。
实体是表的业务化视图,可定义不同的字段和过滤条件
• 示例:物理表销售订单可以定义两个实体:
“全部订单”:包含所有字段
“本年新订单”:仅包含Year(签单日期)=Year(Now())的订单,并只显示订单ID、金额等核心字段
宏字段 查询的最小语义单元,是基础字段的扩展 • 基础字段:直接映射到表字段,如“订单金额”
• 计算字段:通过表达式定义,如BMI指数 = (体重(kg) / 身高(m)²)
• 外键字段:通过关联引入其他表信息,如通过“客户ID”引入“客户名称”
指标 通过表达式定义的聚合度量,用于统计分析 • 简单指标:如“销售总额”(SUM)。
• 复杂指标(SPL):处理SQL不擅长的计算,如“用户留存率”、“股票连涨天数”
字段簇簇词 字段簇是一组业务紧密相关的字段集合
簇词是字段簇的业务别名,用于消除歧义
• 示例:定义“发货”簇(含城市、日期)和“收货”簇(含城市、日期)。
• 应用:用户说“发货 日期”,引擎能精准定位到“发货日期”,而不会与“签单日期”混淆
维词常数词 是分析视角,维词是其业务名,常数词将业务值映射到底层编码 • 示例:将“北京”、“上海”定义为“城市”维的常数词,映射到内部编码(30101, 30102)
• 应用:用户查询“籍贯 北京 的雇员”,引擎自动转换为HOMECITY=30101

NLQ词典 – 特色词型

类别 说明 解释与示例
无效词 过滤掉查询中的口语化虚词和语气词,使引擎聚焦于有效信息 • 示例:“请帮我查一下”、“有哪些”、“那个”。
• 应用:用户输入“请帮我查一下有哪些销售额高的商品”,引擎会忽略加粗部分,直接解析核心意图
宏词 将口语化的业务概念转换为规范的查询过滤逻辑 • 示例:将“已售罄”定义为宏词,其背后逻辑是“库存量 <= 0”
• 应用:用户查询“已售罄的商品”,引擎自动转换为库存量 <= 0
动词 用于建立复杂的过滤逻辑,特别是关联多个字段簇 • 示例:定义动词“发往”,将其左侧关联到“发货”簇,右侧关联到“收货”簇。
• 应用:用户查询“北京 发往 青岛 的订单”,被解析为发货城市=北京 AND 收货城市=青岛。
量词 用于处理带单位的数值,自动进行单位换算 • 示例:定义量词“万元”,换算系数为10000。
• 应用:用户查询“金额大于 20万元”,引擎会自动转换为金额 > 20*10000
比较词与连词 定义过滤关系与条件间的逻辑连接 • 比较词:大于、小于、等于。
• 连词:且、或。
• 应用:支持“年龄大于 40  性别 等于 男”这样的复杂条件组合

NLQ词典-领域知识的完美容器

规则引擎精确查询

  • 抽象汉语规律得到规则模型,建立词典
  • 词典中的词对应查询要素,准确承载了领域知识
  • 把自然语言匹配到词的过程,就是应用领域知识的过程

准确性优势

  • 规则引擎的领域知识就像是“手册”中的明文规定, LLM的知识则是“模糊记忆”
  • 比如“昨日存款总额”,规则引擎可明确定义公式,各币种折合成人民币再汇总

成本优势

  • 词典规模不会查过十几万字符,规则引擎仅用普通CPU运算即可高效处理
  • 规则引擎在普通笔记本电脑都能流畅运行,不需要高端GPU集群,成本很低
语义层

NLQ词典充当语义层 – 智能问数的业务底座

  • 基础支撑

    语义层是所有上层应用的基础
  • 能力上限

    语义层的质量决定了上层应用的能力上限
  • 业务桥梁

    连接业务语言与技术数据的关键

引导式查询与持续数据治理

01 输入侧 · 词汇提示

通过智能联想引导用户规范输入,从源头规避表述歧义

02 输出侧 · 日志反哺

建立“用户查询-日志记录-人工Review-完善词典”的闭环,让语义理解能力随业务持续进化

  • 高频未识别词→加入词典
  • 识别错误词→修正别名
  • 新业务术语→扩展词典

确定性过程促进术语理解

NLQ规则引擎方案

  • 快速验证强条件 + 小范围数据
  • 确认逻辑验证查询逻辑正确性
  • 放心应用放宽条件至全量数据
通过“强条件+小范围数据”快速验证词汇的业务意义,然后可放心放宽条件至大范围数据

纯LLM生成方案

  • 直接查询前置验证无意义
  • 结果存疑生成结果随机可变
  • 难以验证无法复现与核对
概率模型天然缺乏稳定性,不能保证每次结果复现,无法用于术语验证
MQL

MQL引擎:承载复杂查询

类SQL语法 · 精确的语义基准 · 可控的查询范围

四类查询范式

单表明细查询
单表汇总查询
多表明细查询
多表汇总查询

单表明细查询:基础数据筛选

订单金额不低于 1 千元的订单
SELECT 订单金额 as 订单金额,订单编码,客户名称,签单日期,发货日期,收货日期 
FROM orders
WHERE 订单金额>=1000
					

SQL

SELECT
    T_1."AMOUNT"      AS "订单金额",
    T_1."ORDERID"     AS "订单编码",
    T_1."SIGNDATE"    AS "签单日期",
    T_1."SHIPDATE"    AS "发货日期",
    T_1."RECEIVEDATE" AS "收货日期"
FROM
    ORDERS T_1
WHERE
    T_1."AMOUNT" >= 1000;

基于单一数据源且不涉及聚合计算:

  • 字段精确映射:将“订单金额”、“客户名称”等自然语言词汇准确对应到数据库字段
  • 条件准确转换:将“不低于 1 千元”转换为精确的数值比较条件订单金额 >=1000
  • 结果集规范:明确指定需要返回的字段集合

单表聚合查询:维度聚合分析

各城市发货总金额
SELECT orders.sum(订单金额) as 总金额 
ON city as 城市 
FROM orders
BY 发货城市
					

SQL

SELECT
    T_1."SHIPCITY"            AS "城市发货",
    SUM(T_1."AMOUNT")         AS "总金额"
FROM
    ORDERS T_1
GROUP BY
    T_1."SHIPCITY";

引入了维度和聚合的概念:

  • 维度建模:通过 ON city as 城市明确定义分析维度
  • 聚合计算:使用 sum(订单金额) 实现指标汇总
  • 分组逻辑:BY 发货城市 指定了分组依据字段

多表明细查询:关联信息整合

订单数大于5的客户信息和总订单金额
SELECT
    客户编码,客户名称,联系人,联系人职务,城市编码,
    orders.count(DISTINCT 订单编码) AS 订单数,
    orders.sum(订单金额) AS 总订单金额
FROM customer 
JOIN orders 
HAVING (订单数> 5)
					

SQL

SELECT
    T_1.“CUSTID”        AS “客户",
    T_1."CONTACT"       AS "联系人",
    T_1."CONTACTTITLE"  AS "联系人职务",
    T_1."CITYCODE"      AS "城市编码",
    T_2.F_2             AS "订单数",
    T_2.F_3             AS "总订单金额"
FROM
    CUSTOMER T_1
LEFT JOIN (
    SELECT
        T_2."CUSTOMERID"  AS F_1,
        COUNT(1)          AS F_2,
        SUM(T_2."AMOUNT") AS F_3
    FROM
        ORDERS T_2
    GROUP BY
        T_2."CUSTOMERID"
) T_2
    ON T_1."CUSTID" = T_2.F_1
WHERE
    T_2.F_2 > 5;

处理复杂数据关系的能力:

  • 多表关联:通过 JOIN orders 实现客户表与订单表的关联
  • 混合查询:在主表明细基础上挂载子表聚合结果
  • 自动关联:基于元数据自动推导 customer 与 orders 间的关联条件
  • 结果集过滤:通过 HAVING 对结果集进行过滤

多表汇总查询:多项指标对齐

各个类别的订单总数和在线订单数
SELECT orderdetail.count(DISTINCT 订单编码) as 订单总数,
       website_event.sum(在线订单()) as 汇总在线订单数 
ON ProductType as 类别 
FROM orderdetail
BY 产品类别 
JOIN website_event
BY 产品分类

SQL

SELECT
    COALESCE(T_1_2."TYPE", '未分类')            AS "类别",
    COUNT(DISTINCT T_1_1."ORDERID")        AS "订单总数",
    COUNT(DISTINCT CASE 
                       WHEN T_1_3."EVENTTYPE" = 'purchase' 
                       THEN T_1_3."EVENTID" 
                       ELSE NULL    END)                    AS "付款数"
FROM
    ORDERDETAIL T_1_1
LEFT JOIN
    PRODUCT T_1_2
    ON T_1_1."PRODUCTID" = T_1_2."PRODUCTID"
LEFT JOIN
    WEBSITE_EVENT T_1_3
    ON T_1_1."PRODUCTID" = T_1_3."PRODUCTID"
    AND T_1_3."EVENTTYPE" = 'purchase'
GROUP BY
    T_1_2."TYPE"
ORDER BY
    T_1_2."TYPE";

更复杂的指标查询范式:

  • 多源整合:从 orderdetail 和 website_event 两个独立数据源分别计算指标
  • 维度对齐:通过 ON ProductType 实现不同来源数据按统一维度对齐
  • 复杂指标:在线订单() 代表可预定义的业务指标计算

DQL引擎:透明化表间关联

MQL并没有处理业务常见的多对一外键关联,这种情况如何处理?

用户输入
请查询北京发往青岛的订单
LLM转换规范文本:
北京 发往 青岛 订单
NLQ引擎生成MQL:
SELECT 发货城市,收货城市,订单编码,客户名称,签单日期,发货日期,收货日期,订单金额
FROM orders 
WHERE (发货城市=30101) AND (收货城市=20201)
进一步转换成DQL:
SELECT shipcity, customerid.citycode,orderid,customerid,signdate,shipdate,receivedate,amount
FROM orders 
WHERE shipcity=30101 and  customerid.citycode=20201
对象形式表达
DQL引擎生成SQL:
SELECT o.shipcity, c.citycode, o.orderid, o.customerid, o.signdate, o.shipdate, o.receivedate
FROM orders o
JOIN customer c ON o.customerid = c.id
WHERE o.shipcity = 30101 AND c.citycode = 20201
显式关联

SPL引擎:复杂计算

DQL的能力与SQL相当,BI中的复杂计算场景会存在局限,如何应对?

SPL:复杂计算全覆盖

一、跨行组运算

  • 同比环比
  • 累计占比
  • 排名TopN
  • 组内排序

二、复杂指标计算

  • 移动平均
  • 漏斗分析
  • 相关分析
  • 留存复购
  • 滚动累计
  • 帕累托分析
  • 波动率
  • 分位数

基于LLM的对话

小结:各部件的作用

  • 规范文本

    双向可读 DSL,人类可确认
  • NLQ

    业务与数据的桥梁,领域知识的载体,确保100%准确性
  • MQL

    精确承载查询语义,支持复杂查询能力
  • DQL

    透明化表间关联,让用户无需关心 JOIN 逻辑
  • SPL

    处理复杂业务指标计算和跨行运算

NLQ优势总结

  • 灵活性

    可选LLM保持灵活多样语言输入
  • 幻觉可控

    规范文本人类可读可确认
  • 准确性

    基于词典的NLQ引擎转换准确
  • 复杂性

    MQL-DQL-SPL支持复杂查询
  • 高性能

    高性能算法突破数据库性能瓶颈
  • 低成本

    无需GPU普通CPU环境即可部署
实施

NLQ应用结构

构建DQL元数据可视化IDE

构建NLQ词典可视化IDE

LLM辅助生成DQL元数据

DQL元数据和NLQ词典可以借助LLM辅助生成,提高开发效率,降低实施成本

配置LLM

在DQL IDE中填入LLM API信息(URL、模型、密钥)

自动生成元数据

选择生成内容,一键完成DQL元数据创建

  • 自动识别表间主外键关系
  • 自动生成维度、假表等核心结构

人工微调

  • 修正少量表名/字段名翻译
  • 补充缺失的日期外键
  • 调整个别维名
实施成本直降 80%

LLM辅助生成NLQ词典

初始分析

自动生成表/字段中文名、别名、类型、单位、扩展字段

字段簇分析

自动识别字段组合、设置默认字段簇及标记字段

动词分析

识别业务动词,自动关联左右字段簇

簇词分析

为易混淆字段自动生成簇词,简化查询

实施成本直降 70%

NLQ的查询结果还可以

自助报表

查询结果再制作报表

汉语查询结果,直接进行拖拽或命令制表

排名

组内排名

环比

组内环比

外观控制-显示格式

外观控制-条件控制

数据过滤(切片切块)

排序

行列转换

统计图绘制

更改统计图类型

LLM规范-口语化命令

智能规划一次到位

借助LLM将制表任务(口语化)拆分成多个命令,全部或分步执行