【问题标题】:Case statement not working as expected in Oracle案例语句在 Oracle 中未按预期工作
【发布时间】:2014-08-01 15:44:03
【问题描述】:

我在数据库中有一个包含大量空/空行的字段。我正在尝试创建一个 case 语句,将其更改为“空字段”或类似的东西,以便当它显示给用户时,他们将指示该行没有该列的数据,但由于某种原因它不是在职的。当我选择没有 case 语句的数据时,我会得到一个字符串或一个空字段。当我添加 case 语句时,每一行都返回为 {null},无论该列中的内容如何。我曾多次使用类似的案例陈述,但这让我感到困惑。

SELECT CASE
         WHEN col_name = TRIM('') THEN 'Empty Field'
         END col_name
FROM table_name

我还尝试用LIKE 代替等号以及NULL 代替TRIM('')

工作解决方案:

SELECT NVL(TRIM(col_name), 'Empty Field') AS col_name
FROM table_name

【问题讨论】:

  • 您的代码中没有CAST 语句。您的意思是在问题标题中写上CASE 吗? (而TRIM('') 真的没有意义)
  • 操作。是的,我的意思是说CASE,而不是CAST,并更正了它。为什么TRIM('') 不做。我要更改的列是空的或 null。
  • trim() 从字符串中删除前导和尾随空格。字符串''没有任何空格,所以不需要在上面调用trim()

标签: sql oracle


【解决方案1】:

在 Oracle 中,VARCHAR 上下文中的 '' 被视为 NULL

你可以只使用 NVL(col_name,'Default Value')

select NVL(col_name, 'Empty Field') from table_name

TRIM('') 在 Oracle SQL 中为 NULL,所以没有效果。

SQL> set null NULL
SQL> select trim('') from dual;

T
-
N
U
L
L

就您的 CASE 语句而言,问题在于您使用 NULL 相等。你不能说NULL =任何东西,它是错误的。 NULL 不等于任何东西,甚至不等于它本身。你需要使用:

WHERE col_name IS NULL

IS NULL 和 = NULL 是不一样的。

SQL> select case when id = trim('') then 'Empty' end from nulls;

CASEW
-----
NULL

SQL> select case when id = null then 'Empty' end from nulls;

CASEW
-----
NULL

SQL> select case when id is null then 'Empty Field' end from nulls;

CASEW
-----
Empty Field      <--- DATA!

如果这不起作用,也许您的数据中有空格。使用我展示的 SQLPLUS - SET NULL NULL 命令进行测试,以验证它是否真的为 NULL。

【讨论】:

  • 不,在您的 SQL 中,您说过“WHERE col_name = TRIM('')”,就像说“WHERE col_name = NULL”一样,它不会返回任何结果。您无法使用 = 与 NULL 进行比较。您必须改用 IS NULL。有关示例,请参阅我的答案。
  • 如果您要做的只是在值为空时在查询中返回一个默认值,那么您根本不需要 CASE 语句。 Oracle 提供了一个简单的函数 NVL()。为了完整性,我添加了额外的解释。
  • 感谢您向我解释这一点。出于某种原因,NVL() 仍然无法正常工作。我查看了 Oracle 文档,这无疑是最好的解决方案,但似乎正在发生一些奇怪的事情。
【解决方案2】:

您应该按照 codenheim 的建议使用 nvl(),但除了关于您的原始解决方案的答案之外,您没有 else 子句 - 因此没有任何内容与 = null 匹配,并且您永远不会得到 Empty field,但所有不匹配 无论如何都会默认为 null。你需要这样做:

SELECT CASE
     WHEN col_name IS NULL THEN 'Empty Field'
     ELSE col_name
     END AS col_name
FROM table_name

但那将是一样的

SELECT NVL(col_name, 'Empty Field') AS col_name
FROM table_name

您建议仍然无法正常工作,但不是很具体;但是您最初对 trim 的使用让我想知道您是否有一些不为空但仅包含空格的值 - 所以它们之后仍然只是空格。如果是这种情况,并且您想将所有空格视为 null,那么您可以这样做:

SELECT NVL(TRIM(col_name), 'Empty Field') AS col_name
FROM table_name

如果您有其他空格 - 也许只是 tab - 那么您可以使用正则表达式将其去掉,例如:

SELECT NVL(REGEXP_REPLACE(col_name, '^[[:space:]]+$', NULL),
    'Empty Field') AS col_name
FROM table_name;

SQl Fiddle demo.

【讨论】:

  • 这让我觉得他有一个带有空格的 CHAR() 字段。
  • 为了澄清使用NVL() 时“仍然无法正常工作”,它返回的结果与我根本没有使用它一样。您怀疑空格是否正确。我使用了VL(TRIM(col_name), 'Empty Field'),效果很好。谢谢!
【解决方案3】:

正确的做法是使用 codenheim 示例。但是为了清楚起见,当您在 oracle 中检查 NULL 列时,您必须使用 IS NULL

SELECT CASE
     WHEN col_name IS NULL THEN 'Empty Field'
     ELSE col_name
     END AS col_name
FROM table_name;

【讨论】:

  • 这会将每一行返回为{null}。我知道这应该可行,但由于某种原因,它不是。
猜你喜欢
  • 2020-03-05
  • 2017-10-27
  • 1970-01-01
  • 1970-01-01
  • 2012-08-16
  • 2020-03-11
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多