【问题标题】:PL/SQL extract SELECT statement column names from custom queryPL/SQL 从自定义查询中提取 SELECT 语句列名
【发布时间】:2018-03-13 08:43:31
【问题描述】:

我有一个自定义查询,我需要知道如何从中提取列名。我已经搜索过任何方法来做到这一点:

  • Regex:我已经构建了 this 一个来获得或多或少我想要的东西,但它不起作用(我使用的是 Toad 12.6.0.53)。

这是我尝试测试我的正则表达式的代码:

DECLARE
  v_SQL VARCHAR2(32767 CHAR);
  v_Result VARCHAR2(32767 CHAR);
BEGIN 
  v_SQL := 'SELECT 
  ALIASBASE.CDCMPANY, 
  ALIASBASE.PAFCODCTR, 
  ALIASBASE.PAFDTSCAD, 
  NUMFLUSSO.NUMERO, 
  ALIASBASE.PAFDESC, 
  ALIASBASE.PAFTYPE, 
  ALIASBASE.PAFNATURE, 
  ALIASBASE.PAFRECEIV, 
  ALIASBASE.PAFCAUSAL, 
  ALIASBASE.PAFCODDNE, 
  ALIASBASE.PAFMATURITY
  FROM ALBSIAE';

  BEGIN
    SELECT 
      REGEXP_SUBSTR (v_SQL, '(?:\s*(?=\w+\.|.*as\s+|)(\*|\w+)(?=\s*(?=,|from)))',1, NULL,'i') REGEX_RESULT 
    INTO
      v_Result
    FROM DUAL;
  END;

  DBMS_OUTPUT.put_line('v_Result: ' || v_Result);
END;

但是最后 v_Result 是空的。

  • 另一种方法是在我的表格列之间循环,正如我所看到的 here 和 here,但我认为不是我的情况。

所以,我想知道是否有其他方法可以做到这一点,我的正则表达式错了吗?有什么问题吗? Oracle 还有其他正则表达式语法吗?

【问题讨论】:

  • 试试REGEXP_SUBSTR(v_SQL, '(\*|[[:alnum:]_]+)(\s*(,|from))', 1, 1, 'i', 1)
  • 只有在简短的简单查询的情况下,它才会与正则表达式一起使用。 WITH 子句或SELECT 子句中的复杂计算将阻止此解决方案。更好的解决方案是使用dbms_sql 包(docs.oracle.com/cloud/latest/db121/ARPLS/d_sql.htm#ARPLS058)。
  • 感谢@WiktorStribiżew。你能解释一下语法吗?
  • 我想你需要看看其他解决方案。正则表达式 - 即使已修复 - 很可能会导致进一步的问题。

标签: sql regex oracle plsql


【解决方案1】:

您可以使用 DBMS_SQL.parse 解析语句并使用 DBMS_SQL.describe_columns 获取列:

DECLARE
  v_SQL VARCHAR2(32767 CHAR);
  v_Result VARCHAR2(32767 CHAR) := '';
  l_cursor        PLS_INTEGER;
  l_col_cnt       PLS_INTEGER;
  i               PLS_INTEGER;
  l_desc_tab      DBMS_SQL.desc_tab;
BEGIN 
  v_SQL := q'[SELECT 1 as "MY_NUMBER", 'z' as "MY_CHAR" from dual]';
  l_cursor := DBMS_SQL.open_cursor;
  DBMS_SQL.parse(l_cursor, v_SQL, DBMS_SQL.native);
  DBMS_SQL.describe_columns(l_cursor, l_col_cnt, l_desc_tab);

  FOR i IN 1 .. l_col_cnt LOOP
    v_Result := v_Result ||' ' || l_desc_tab(i).col_name;
  END LOOP;

  DBMS_OUTPUT.put_line('v_Result: ' || v_Result);

END;
/

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-12-06
    • 2015-08-28
    • 2012-02-14
    • 1970-01-01
    相关资源
    最近更新 更多