首页 > 解决方案 > Oracle 12c 数据默认值

问题描述

Oracle Database 12c Enterprise Edition Release 12.1.0.2.0 - 64bit Production

桌子:

CREATE TABLE t1 (
  c1 VARCHAR2(100 CHAR) DEFAULT 'SOME DATA' NOT NULL, 
  c2 DATE DEFAULT SYSDATE NOT NULL, 
  c3 NUMBER DEFAULT 10 NOT NULL);

选择:

BEGIN
  FOR c IN (SELECT * FROM user_tab_columns WHERE table_name = 'T1') LOOP
    DBMS_output.put_line('"' || c.data_default || '"');
  END LOOP;
END;

结果:

"'SOME DATA' "
"SYSDATE "
"10 "

为什么末尾有空格DATA DEFAULT?我需要将 Oracle 字典中的数据默认值与项目元数据中的数据默认值进行比较,但是这个空间破坏了比较。

编辑: @GordonLinoff 询问“额外的字符真的是空格吗?” 由于列的LONG数据类型,DATA_DEFAULT我发现只有一个测试:

DECLARE
  l_ret   VARCHAR2(32000);
  l_dump  VARCHAR2(32000);
BEGIN
  FOR c IN (SELECT * FROM user_tab_columns WHERE table_name = 'T1') LOOP
    DBMS_output.put_line('"' || c.data_default || '"');
    l_ret := c.data_default;
    SELECT dump(l_ret) 
      INTO l_dump
      FROM dual;
    DBMS_output.put_line(l_dump);
  END LOOP;
END;

结果:

"10 "
Typ=1 Len=3: 49,48,32
"SYSDATE "
Typ=1 Len=8: 83,89,83,68,65,84,69,32
"'SOME DATA' "
Typ=1 Len=12: 39,83,79,77,69,32,68,65,84,65,39,32

所以,它是一个空间 (32)。

标签: sqlstringoracleplsqloracle12c

解决方案


有趣的。

一个简单的测试表明,仅当您为其定义默认值的列声明为 NOT NULL 时,才会添加额外的空间。(因此,与@GordonLinoff 推测的相反,这不是将默认值存储为 LONG 的产物。)

为什么甲骨文这样做……谁知道呢。

在任何情况下,当您将字典中的默认值与您的规范(项目元数据)进行比较时,最简单的解决方案似乎是在比较的另一个术语的末尾有条件地添加一个尾随空格。(以列是否为 NOT NULL 为条件。)

或者,如果您确实需要直接操作声称的默认值,您还可以从 USER_TAB_COLUMNS 检索 DEFAULT_LENGTH 值,这样您就可以轻松地仅删除尾随空格(当列不可为空时),同时保留任何可能的尾随空格实际的,所需的默认值的一部分。(例如:非 NULL 文本列的默认值正好是一个空格;DEFAULT_VALUE 报告为两个空格,您只想修剪第二个空格,而不是第一个。)


推荐阅读