PLSQL 在数据库中搜索值

问题描述 投票:0回答:1

我最近从非常了解 MSSQL 转向使用 PLSQL。我在 MSSQL 中拥有的一组真正有用的脚本是用于理解没有可用文档或建议的数据库结构(遗憾的是,这种情况经常出现)。这些工具之一是用于在数据库中搜索特定值(例如 ID)的脚本。我正在尝试为 PLSQL 复制该脚本。我在这里尝试开发的脚本是搜索整数值。

我采用的方法是创建一个由架构/表/数字列组成的临时表,然后创建动态 SQL 来计算每个实例中有多少行包含我正在搜索的值。最后,我选择匹配数大于零的行。我在脚本中声明临时表时遇到困难。我正在使用 SQL 开发人员。到目前为止我的脚本如下。

DECLARE cSQL VARCHAR2(1000);
        iSearchValue INT;

CREATE PRIVATE TEMPORARY TABLE ORA$PTT_COL_MATCHES
(
    SCHEMA_NAME VARCHAR2(100),
    TABLE_NAME VARCHAR2(100),
    COLUMN_NAME VARCHAR2(100),
    DATA_TYPE VARCHAR2(100),
    MATCH_COUNT INT
)
ON COMMIT PRESERVE DEFINITION;

BEGIN
    iSearchValue := 237001;
    
    
    INSERT INTO ORA$PTT_COL_MATCHES
            (SCHEMA_NAME,
            TABLE_NAME,
            COLUMN_NAME,
            DATA_TYPE,
            MATCH_COUNT)
    SELECT  col.owner as schema_name,
            col.table_name, 
            col.column_name,
            col.data_type,
            0
    FROM    sys.all_tab_columns col
            INNER JOIN sys.all_tables t     ON      col.owner = t.owner 
                                            AND     col.table_name = t.table_name
    WHERE   col.owner NOT IN ('SYS', 'SYSTEM');
    --AND     col.DATA_TYPE IN ('INT', 'NUMBER', 'FLOAT', 'LONG')
            
            
    FOR rec IN
        (SELECT  *
        FROM    ORA$PTT_COL_MATCHES)
    LOOP
        cSQL = 'UPDATE  ' || ORA$PTT_COL_MATCHES || '
                SET     MATCH_COUNT = (SELECT COUNT(*) FROM ' || rec.SCHEMA_NAME || '.' || rec.TABLE_NAME || ' WHERE ' || rec.COLUMN_NAME || ' = ' || TO_CHAR(iSearchValue) || ')
                WHERE   SCHEMA_NAME = ''' || rec.SCHEMA_NAME || '''
                AND     TABLE_NAME = ''' || rec.TABLE_NAME || '''';
        EXECUTE IMMEDIATE cSQL;
    END LOOP;
    
    
    SELECT  *
    FROM    ORA$PTT_COL_MATCHES
    WHERE   MATCH_COUNT > 0;
    
    
END;

我收到的错误是:

Error report -
ORA-06550: line 4, column 1:
PLS-00103: Encountered the symbol "CREATE" when expecting one of the following:

   begin function pragma procedure subtype type <an identifier>
   <a double-quoted delimited-identifier> current cursor delete
   exists prior
06550. 00000 -  "line %s, column %s:\n%s"
*Cause:    Usually a PL/SQL compilation error.
*Action:

在 SQL Developer 中,我手动选择要执行的整个脚本。据我了解,上述错误表明我无法在脚本中的此时使用 CREATE。我的问题是:

  1. 为什么我不能在那里创建临时表,并且
  2. 我在哪里可以创建它,因为 BEGIN-END 块内部也不起作用?
  3. 额外问题:在 PLSQL 中是否有更好的方法来做到这一点?
search plsql oracle-sqldeveloper temp-tables
1个回答
0
投票

CREATE TABLE
是DDL语句,不能在PL/SQL中使用DDL语句。您需要在 PL/SQL 块之前执行此操作或使用
EXECUTE IMMEDIATE
。同样,您不能在 PL/SQL 块中单独使用
SELECT
语句;您需要
SELECT ... [BULK COLLECT] INTO ...
或使用带有
SELECT
的光标:

CREATE PRIVATE TEMPORARY TABLE ORA$PTT_COL_MATCHES
(
    SCHEMA_NAME VARCHAR2(100),
    TABLE_NAME VARCHAR2(100),
    COLUMN_NAME VARCHAR2(100),
    DATA_TYPE VARCHAR2(100),
    MATCH_COUNT INT
)
ON COMMIT PRESERVE DEFINITION;

DECLARE
  cSQL         VARCHAR2(1000);
  iSearchValue INT;
BEGIN
  iSearchValue := 237001;
    
  INSERT INTO ORA$PTT_COL_MATCHES
          (SCHEMA_NAME,
          TABLE_NAME,
          COLUMN_NAME,
          DATA_TYPE,
          MATCH_COUNT)
  SELECT  col.owner as schema_name,
          col.table_name, 
          col.column_name,
          col.data_type,
          0
  FROM    sys.all_tab_columns col
          INNER JOIN sys.all_tables t     ON      col.owner = t.owner 
                                          AND     col.table_name = t.table_name
  WHERE   col.owner NOT IN ('SYS', 'SYSTEM');
  --AND     col.DATA_TYPE IN ('INT', 'NUMBER', 'FLOAT', 'LONG')
            
  FOR rec IN
        (SELECT  *
        FROM    ORA$PTT_COL_MATCHES)
  LOOP
      cSQL = 'UPDATE  ' || ORA$PTT_COL_MATCHES || '
              SET     MATCH_COUNT = (SELECT COUNT(*) FROM ' || rec.SCHEMA_NAME || '.' || rec.TABLE_NAME || ' WHERE ' || rec.COLUMN_NAME || ' = ' || TO_CHAR(iSearchValue) || ')
              WHERE   SCHEMA_NAME = ''' || rec.SCHEMA_NAME || '''
              AND     TABLE_NAME = ''' || rec.TABLE_NAME || '''';
      EXECUTE IMMEDIATE cSQL;
  END LOOP;
END;
/

SELECT  *
FROM    ORA$PTT_COL_MATCHES
WHERE   MATCH_COUNT > 0;
© www.soinside.com 2019 - 2024. All rights reserved.