【问题标题】:Convert LONG into VARCHAR2 or some text datatype将 LONG 转换为 VARCHAR2 或某些文本数据类型
【发布时间】:2015-03-06 06:30:38
【问题描述】:

众所周知,LONG 很久以前在 Oracle 中已被弃用,但 Oracle 本身仍在他们的视图中使用这种数据类型。

因此,如果我必须将 LONG 更改为某种文本数据类型,我该如何实现。

我正在尝试查询这个并得到错误。

ORA-00932: inconsistent datatypes: expected - got LONG

查询-

SELECT NVL(ie.column_expression, ic.column_name)
from user_ind_columns ic left join user_ind_expressions ie  on ic.index_name = ie.index_name and ic.table_name = ie.table_name 
where ic.table_name = 'Some Table'

【问题讨论】:

    标签: sql oracle oracle11g long-integer type-conversion


    【解决方案1】:

    有几种方法,一种是create table 使用TO_LOB。它旨在将 LONG 或 LONG RAW 列分别转换为 CLOB 或 BLOB。其他方法使用PL/SQLDBMS_XMLGEN。您也可以在插入语句中使用TO_LOB

    让我们看看如何将LONG转换成CLOB-

    SQL> CREATE TABLE t (x INT, y LONG);
    
    Table created.
    
    SQL>
    SQL> INSERT INTO t VALUES (1, RPAD('*',9,'!'));
    
    1 row created.
    
    SQL> INSERT INTO t VALUES (2, RPAD('*',9,'@'));
    
    1 row created.
    
    SQL> INSERT INTO t VALUES (3, RPAD('*',9,'#'));
    
    1 row created.
    
    SQL> COMMIT;
    
    Commit complete.
    
    SQL>
    

    所以,我们有一个表 t,其中列 y 是 LONG 数据类型。

    SQL> CREATE TABLE t1
      2  AS
      3  SELECT * FROM t
      4  /
    SELECT * FROM t
           *
    ERROR at line 3:
    ORA-00997: illegal use of LONG datatype
    
    SQL>
    

    我们可以看到 LONG 限制。

    让我们使用TO_LOB 将其转换为CLOB

    SQL> CREATE TABLE t1
      2  AS
      3  SELECT x,
      4         to_lob(y) as y
      5  FROM t
      6  /
    
    Table created.
    
    SQL> desc t1;
     Name                                                  Null?    Type
     ----------------------------------------------------- -------- ------------------------------------
     X                                                              NUMBER(38)
     Y                                                              CLOB
    
    SQL>
    

    现在您拥有同一张表,其中LONG 列转换为CLOB

    【讨论】:

      【解决方案2】:

      这很愚蠢(可能效率不高),但它适用于 y 的小长度(即

      CREATE TABLE t (x INT, y LONG);
      
      INSERT INTO t VALUES (1, RPAD('*',9,'!'));
      
      CREATE TABLE t1
      AS
      SELECT x,
             regexp_substr(SYS.DBMS_XMLGEN.GETXML('select y from t where rowid = '''||rowid||''''),'<Y>(.*)</Y>',1,1,'in',1) y
      FROM t
      /
      

      它的工作原理是使用 dbms_xmlgen 根据 LONG 列生成一个 clob。然后将值返回。

      这仅适用于 LONG 列的小内容。但这就是我所拥有的,这对我有用。

      【讨论】:

        【解决方案3】:

        我有类似的需求,列出对象及其大小(包括索引中使用的列的信息),并提供了以下解决方案:

        
        select idx1.table_owner owner, idx1.table_name, idx1.index_name, listagg(nvl(idx1.column_expression,idx1.column_name),',') within group (order by idx1.column_position) column_name
        from xmltable(
            '/ROWSET/ROW'
            passing (select dbms_xmlgen.getxmltype('select ic.table_owner, ic.table_name, ic.index_name, ic.column_position, ic.column_name, ie.column_expression
            from all_ind_columns ic
            left outer join dba_ind_expressions ie on ie.table_owner=ic.table_owner and ie.table_name=ic.table_name and ie.index_name=ic.index_name and ie.column_position=ic.column_position') from dual)
            columns index_name varchar2(30) path 'INDEX_NAME'
                , table_owner varchar2(30) path 'TABLE_OWNER'
                , table_name varchar2(30) path 'TABLE_NAME'
                , column_position number path 'COLUMN_POSITION'
                , column_name varchar2(30) path 'COLUMN_NAME'
                , column_expression varchar2(4000) path 'COLUMN_EXPRESSION') idx1
        group by idx1.table_owner, idx1.table_name, idx1.index_name
        

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 2016-03-10
          • 2018-04-10
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2021-03-13
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多