sql >> Database teknologi >  >> RDS >> Oracle

CLOB vs. VARCHAR2 og er der andre alternativer?

Det er en meget dårlig idé at bruge en CLOB-datatype til en kolonne, som burde være VARCHAR2(1). Bortset fra de faste omkostninger (som faktisk er minimale, da Oracle vil behandle inline CLOB'er på <4000 tegn som VARCHAR2) bør vi altid stræbe efter at bruge den mest nøjagtige repræsentation af vores data i skemaet:det er bare god praksis.

Dette virker virkelig som et problem med DevArt-værktøjet, eller måske din forståelse af, hvordan man bruger det (ingen fornærmelse). Der burde være en måde, hvorpå du kan specificere datatypen for en enheds attribut og/eller en måde at kortlægge disse specifikationer til Oracles fysiske datatyper. Jeg beklager, hvis dette virker lidt vagt, jeg er ikke bekendt med produktet.

Så dette er det grundlæggende problem:

SQL> desc t69
 Name                                      Null?    Type
 ----------------------------------------- -------- --------
 COL1                                               CLOB

SQL>
SQL> alter table t69 modify col1 varchar2(1)
  2  /
alter table t69 modify col1 varchar2(1)
                       *
ERROR at line 1:
ORA-22859: invalid modification of columns


SQL>

Vi kan rette det ved at bruge DDL til at ændre tabelstrukturen. Fordi skemaet har mange sådanne kolonner, er det umagen værd at automatisere processen. Denne funktion sletter den eksisterende kolonne og genskaber den som en VARCHAR2. Det giver mulighed for at migrere data i CLOB-kolonnen til VARCHAR2-kolonnen; du har sandsynligvis ikke brug for dette, men det er der for fuldstændighedens skyld. (Dette er ikke produktionskvalitetskode - det kræver fejlhåndtering, håndtering af IKKE NULL-begrænsninger osv.)

create or replace procedure clob2vc
  ( ptab in user_tables.table_name%type 
    , pcol in user_tab_columns.column_name%type
    , pcol_size in number
    , migrate_data in boolean := true )
is
begin
    if migrate_data
    then
        execute immediate 'alter table '||ptab
                    ||' add tmp_col varchar2('|| pcol_size|| ')';
        execute immediate             
                    'update '||ptab
                    ||' set tmp_col = substr('||pcol||',1,'||pcol_size||')';
    end if;
    execute immediate 'alter table '||ptab
                ||' drop column '|| pcol;

    if migrate_data
    then
        execute immediate 'alter table '||ptab
                    ||' rename column tmp_col to '|| pcol;
    else
        execute immediate 'alter table '||ptab
                    ||' add '||pcol||' varchar2('|| pcol_size|| ')';
    end if;
end;
/

Så lad os ændre den kolonne...

SQL> exec clob2vc ('T69', 'COL1', 1)

PL/SQL procedure successfully completed.

SQL> desc t69
 Name                                      Null?    Type
 ----------------------------------------- -------- ---------------
 COL1                                               VARCHAR2(1)

SQL>

Kaldning af denne procedure kan automatiseres eller scripts på de sædvanlige måder.



  1. pdo forberede undslippende enkelt citater

  2. Dynamisk SQL - EXEC(@SQL) versus EXEC SP_EXECUTESQL(@SQL)

  3. MySQL COALESCE() Forklaret

  4. Sådan skriver du Ordre efter-klausul før Hvor-klausul