注:本篇写于chatgpt还没火的2022年左右

目录

  1. 已尝试的算法
    1. RATSQL
    2. IRNET
  2. 数据集
    1. NL2SQL
    2. DuSQL
    3. CSGSQL
  3. 训练模型方案
    1. DuSQL
    2. DuSQL+NL2SQL
    3. (DuSQL/DuSQL+NL2SQL) + CSGSQL
    4. CSGSQL
  4. 迁移其它领域问题
    1. 表格选择
    2. value提取
    3. db file依赖
    4. 训练速度
    5. 标注成本和工具
    6. 应用在问答中
    7. 结果展示问题
  5. 应用方向
    1. 通用服务
    2. 新领域(带标注)

1. 已尝试的算法

1. RATSQL

2. ValueNET

其中RATSQL较为推荐,是微软20年的工作,ValueNET是来自于微软19年IRNet的工作的改进,因此主要是以RATSQL为主要方案。

2. 数据集

1. NL2SQL

该数据集是中文领域第一个较大的数据集,格式类似于wikisql,主要是针对单表简单SQL(形如SELECT xx FROM xx WHERE xx的形式)进行处理

2. DuSQL

该数据集是中文领域又一个较大的数据集,由百度提供和维护,该数据集涵盖的SQL范围较为广泛,能够解决跨表格和复杂形式的SQL处理,是现在训练模型的主力数据集。但由于来源于百度,商用方案需要注意是否造成一定风险。

3. CSGSQL

该数据集是电力行业相关数据,可以认为是特定领域的数据集。因此在该数据集上进行验证实验,有较强的说明性,可以作为跨领域的一次有效尝试。

该数据集在是适配现有方案的时候主要发现了以下的问题:

  • 提供的数据格式不同
    • table name、column name给定的是英文,模型支持中文
    • 标注的SQL语句的列名等内容是英文,模型支持中文
    • 给定的db content的列名等内容是英文,模型支持中文
    • 以上问题能够通过转换脚本解决
  • 提供一个数据库数据,包含有46张数据表。但现有标注数据通常仅包含小于10个的数据表,因此难以直接适配现有模型。

3. 训练模型方案

对于RATSQL模型为了减少一些玄学影响,我们将验证集进行二次划分,分为dev_when_trainingdev_after_training,即在训练中进行预测的验证集和完成训练后的验证集。

因此,可以利用现有的数据训练两种模型,即DuSQL训练的模型(已做)和DuSQL+NL2SQL数据集(未做)训练的模型。然后对比二者的性能,选择效果较好的进入迁移的环节,由于仅实验DuSQL,所以以下以DuSQL数据集为例进行阐述。

对于新领域数据(如CSGSQL),我们可以用如下方案确定最优方案:

  1. 对CSGSQL划分为训练集、验证集一(when training)、验证集二(after training)
  2. 分别使用DuSQL数据训练的模型、CSGSQL训练集得到的模型、DuSQL+CSGSQL混合训练得到的模型,在两个验证集上面得到指标
  3. 确定最优的方案

结果(exact-match):

  1. CSGSQL训练

image

  1. CSGSQL+DuSQL训练

image

说明:

  • CSGSQL结果中在后面的epoch指标掉下去没有起来,猜测一个原因是训练数据过少导致(貌似有人提到过RATSQL有时候会训练不成功,并且这种情况的确发生过)
  • 主要以exact match为主,执行准确率由于没有针对CSGSQL训练单独的value提取模型所以暂时不考虑
  • 主要可以观察all维度的性能,基本上在0.7以上,大于DuSQL的结果
  • CSGSQL+DuSQL的exact match in dev_2的all数据有点问题,还没解决
  • 一个大胆的猜想:由于DuSQL数据本身难度较高,模型没有在这个模型上达到最优的效果,因此混合训练反而会拖累一些效果。因此可以考虑将DuSQL得到的模型当作通用服务来使用,而特定领域的数据还是以标注-训练的方式来实现较好。

4. 迁移其它领域问题

1. 表格选择

如CSGSQL数据集描述中所说,最大的问题是在于该数据集仅提供了一个包含46张表格的数据库,所以对于已有的RATSQL模型,不能够直接将Question+Table Schema进行输入。因此需要用一定的方案来解决Schema输入的问题,即确定输入的Question所依赖的数据表。

根据之前的实验,总结方案如下:

  1. 对于确定数据库但是不确定数据表的情况

    1. 构建训练数据:
      • Input: Question[SEP]Table Name
      • Output: True/False
    2. usage:新输入的Question,对候选的每个Table Name进行二分类的判别
    3. 选择所有判断为True(相关)的Table Name,按照相应的格式重新组成db schema
    4. 类似地,还可以通过相关性的排序模型或一个多标签分类模型解决这个问题
  2. 对于不确定数据库且不确定数据表的情况

    可以采用类似于上面的方案,也可以通过元数据图谱来尝试。

方案1仅仅考虑了问题的文本和表格/列的名称,没有考虑表格更详细的内容,如果可以通过一些方法提取表格内容的信息或者特征,在训练分类器的时候加入,应该会有进一步的提升。但是现有的

2. value提取

对于RATSQL模型来说,其输出的SQL语句是不包含where组件的value值的,例如:

SELECT 发电厂基本信息.电子邮箱 FROM 发电厂基本信息 WHERE 发电厂基本信息.发电厂名称 = ‘terminal’

其中terminal则是模型输出固定用于替换value部分的文本片段。根据论文的描述,如果同时令模型学习value的抽取,效果会有一定的下降,因此我们考虑另一种方案来解决value提取的问题。可采用方案如下:

  1. 按照序列标注的思想解决
    1. 构建训练数据
      • Input: Question[SEP]Column Name
      • Output: text span
    2. usage:根据Question和模型生成的Column Name,抽取相应的值,完成SQL语句的填充
  2. 指针网络

    类似于x-sql论文描述,未实际实验

对比了在DuSQL数据集训练的value抽取模型在CSGSQL数据的效果,可以观察到明显的不能正常work,因此,对于新的领域,可以用已有value提取模型进行尝试,但为了更好的完成相关任务,应该重新训练适配新领域的模型来使用

3. db file依赖

参考Spider官网的排名可以看到,在各个排行榜上经常有出现(DB content used)的标记,即该方法使用了数据库数据表的具体内容,不论是进行了检索或者是编码。

对于RATSQL模型来说,默认的配置也是使用db content的,而这一点对于实验室数据影响不大,但是在实际应用中容易出现较大的问题。例如RATSQL会根据db file来获取schame信息(这点可以进行替换修改),但是也会在训练或eval之前将db file的内容读取至内存(这是个处理的难点)。

对于实验室常用的sqlite数据库来说影响较小,因为往往使用sqlite的项目都不是较大,但是考虑到实际生产中多数是较大的数据库或者数据表,甚至可能包含pg或者excel表格的洞察,那么这个问题就比较明显了。

目前阶段对于RATSQL来说,有个cv_link的参数控制是否获取数据库表格内容(即论文4.3章,Value-Based Linking部分),然而根据以前的实验,不使用db content(cv_link=False)会一定程度上影响模型效果,因此这一点还需要进一步的优化实验,但是从实用性角度来考虑,可以先暂时牺牲少部分指标性能,增加支持的广度

4. 训练速度

按照现有的max_step=80000的设置,完成所有的训练步骤通常需要一周以上的时间,而根据以前的实验,通常在step≈40000时开始收敛,模型效果逐渐趋于稳定。因此,对于需要重新训练的新领域数据来说,可以适当地减少训练步数,当趋向稳定时停止训练,减少总体消耗时间

5. 标注成本和工具

对于新的领域,如果希望标注新数据从而令模型能够更好地适配,往往会提出由业务人员标注部分数据。但是这将涉及两方面的数据的收集:

  1. 问题的收集:对于问题的构建,需要设想SQL语句能够解决的问题,即不能凭空想象问题,构建不能写出SQL语句的问题对事情没有任何帮助。
  2. SQL语句的编写:可以利用现有模型生成一批预生成的SQL语句,再由标注人员进行修改,但是难点在于需要标注人员有一定的SQL储备,还需要保证标注的SQL语句能够被真正地正确执行。

对于标注工具,最简单的可以用Excel进行标注,如果希望采用标注系统进行标注,可以考虑系列机器翻译的标注工具,例如:doccano,之前对这个工具进行过部署尝试,可参考:本博客有一篇踩坑

6. 应用在问答中

NL2SQL/Text to SQL 问题还有个别名就是表格问答,因此NL2SQL天然适合与问答系统结合,但是带来的问题也较多。在目前阶段,NL2SQL较适合单轮问答的场景,对于多轮问答还有较多的挑战性。

  • 在单轮问答中可能的问题如:
    • 什么时候出发NL2SQL模块
    • 如合将NL2SQL的结果进行包装返回
    • 对于问答系统往往对实时性要求较高,如合确保NL2SQL的效率
    • 对于问答系统来说,一定的场景下难以获取用户是针对某个表格进行提问,如果是开放域的问题,整个确定表格+SQL生成的流程很长
  • 在多轮问答中可能有的问题如:
    • 多轮问答中,query的省略与补全
      • Q1:小明在2021年的工时有多少?
      • Q2:那小萌呢?
      • 补全/改写后:小萌在2021年的工时有多少?
    • 多轮问答中,query中代词的消解处理
      • Q1:小明的2021年的工时有多少?
      • Q2:他的部门是什么?
      • 消解/改写后:小明的部门是什么?

因此,对于NL2SQL与问答系统结合,还是一个需要更进一步的尝试和设计。

7. 结果展示问题

通常对于SQL执行的结果有两大类,第一是独立的计算后的值,第二是返回一部分二维表。因此可以设定一些规则对结果做预定义好的展示,但是这种展示形式由业务方进行确定较为合适,因为使用场景和业务场景是由业务人员确定的。

5. 应用方向

1. 通用服务

以DuSQL为基础,形成一个服务,使其可以接受任意的输入并返回结果。

该服务可以用于poc或者不适合标注的项目,或者用于预标注些数据用于训练模型。

2. 新领域(带标注)

  1. value提取模型的训练
  2. 用通用数据进行预标注,然后人工标注数据,注意最好在标注前期划分好训练集和测试集,测试集由业务人员确认,可以不暴露给开发人员
  3. 训练模型,用测试数据进行测试,尽量在调试阶段不接触或减少对测试集的接触(调错除外)

附:之前给某个项目写的工时及风险预估

一、前置任务:候选表格筛选任务,属于分类任务。如果提供标注数据,需要5人日;如果不提供标注数据则不需要额外工时,但对最终结果的准确率存在影响,因为没有公开数据集训练的通用模型可迁移至该领域数据。

二、模型部分

1.1类问题:5人日,候选方案:x-sql

1.2,2.1可考虑为同类问题,主要是对SQL语句的SELECT组件部分进行处理,如:SELECT SUM/AVG 某一列名称。
若输入问题条件较少,至少需要5人日,候选方案:x-sql。
若输入问题的条件数量较多或问题较为复杂,那么需要10~15人日。候选方案:ratsql/valuenet。

2.2,2.3,2.4类问题需要对SQL语句的WHERE组件进行处理,由于组合方式较多,至少需要15人日。候选方案:ratsql/valuenet。

补充:

  1. 对每类问题提供若干示例问法有助于模型调整,若该问题需要跨多表需要进行提示(跨3个表是模型极限),如果不提供则需要算法测人员自行理解业务,工时需要增加。
  2. 对于提供的数据及schema,对于日期列(如年份月份日期)需要明确格式,如yy-mm-dd/yy.mm.dd等,这将直接影响最终返回结果。
  3. 对于数量相关的列,需要明确单位,如吨/万吨等。
  4. 数据处理可能产生的工作量由拿到的最终数据决定,结合理解业务可能产生的工时,该部分建议至少增加5人日。

综上,大约需要45人日(5+5+15+15+5)

又及,如果要做这个事情建议前期约定好问题类型,否则存在后期对问题种类不明确界定的扯皮风险。