这是我的用例:输入是表示任意复杂度的Oracle PL/SQL 语句的字符串。我们可以假设它是单个语句(不是脚本)。现在,这个输入字符串的几个位必须被重写。
例如,表名需要加上前缀,选择列表中不使用列别名的聚合函数应该被分配一个默认值:
SELECT SUM(ABS(x.value)),
TO_CHAR(y.ID,'111,111'),
y.some_col
FROM
tableX x,
(SELECT DISTINCT ID
FROM tableZ z
WHERE ID > 10) y
WHERE
...
变成
SELECT SUM(ABS(x.value)) COL1,
TO_CHAR(y.ID,'111,111') COL2,
y.some_col
FROM
pref.tableX x,
(SELECT DISTINCT ID, some_col
FROM pref.tableZ z
WHERE ID > 10) y
WHERE
...
(免责声明:只是为了说明问题,声明没有意义)
由于聚合函数可能是嵌套的,而 subSELECTs 是一个 b_tch,我不敢使用正则表达式。好吧,实际上我做到了并取得了 80% 的成功,但我确实需要剩下的 20%。
我认为正确的方法是使用语法和解析器。我摆弄了 c++ ANTLR2(尽管我对语法和在这些帮助下的解析知之甚少)。我看不到获取 SQL 位的简单方法:
list<string> *ssel = theAST.getSubSelectList(); // fantasy land
任何人都可以提供一些关于“解析专业人员”如何解决这个问题的指示吗?编辑:我正在使用Oracle 9i。