简体   繁体   English

如何在没有 NULL 结果的情况下连接值(雪花)

[英]How to concat values without NULL results (Snowflake)

I'm trying to concat not null values in Snowflake.我试图在雪花中连接不是 null 值。

My current code:我当前的代码:

            CONCAT(
                CASE WHEN Red='TRUE' THEN 'Red, ' ELSE '' END ||
                CASE WHEN Blue='TRUE' THEN 'Blue, ' ELSE '' END ||
                CASE WHEN Black='TRUE' THEN 'Black, ' ELSE '' END ||
                CASE WHEN White='TRUE' THEN 'White, ' ELSE '' END)

Return: 
Red, White, Black,
Black,
...

Want:
Red, White, Black
Black

In Mysql, I would use Concat_WS, but in Snowflake if one value is NULL, NULL will be in Return:在 Mysql 中,我会使用 Concat_WS,但在 Snowflake 中,如果一个值为 NULL,NULL 将返回:

            CONCAT_WS(', ',
                CASE WHEN Red='TRUE' THEN 'Red' ELSE NULL END,
                CASE WHEN Blue='TRUE' THEN 'Blue' ELSE NULL END,
                CASE WHEN Black='TRUE' THEN 'Black' ELSE NULL END,
                CASE WHEN White='TRUE' THEN 'White' ELSE NULL END)

A bit late, but I had the same problem and found a different solution:有点晚了,但我遇到了同样的问题并找到了不同的解决方案:

As was rightly pointed out before CONCAT and WS_CONCAT always return NULL when any argument to them is NULL .正如之前正确指出的那样,当CONCATWS_CONCAT的任何参数为NULL时,它们总是返回NULL

But, as Snowflake has a concept of ARRAY s (ie support for semi-structured data), ie we can do the following:但是,由于 Snowflake 具有ARRAY的概念(即支持半结构化数据),即我们可以执行以下操作:

  1. Collect the raw values into an array with array_construct使用array_construct将原始值收集到一个数组中
  2. Remove NULL values from the array with array_compact使用array_compact从数组中删除NULL
  3. Use array_to_string to concatenate the remaining array items into a string使用array_to_string将剩余的数组项连接成一个字符串

Here's the modifief code, using arrays:这是修改代码,使用 arrays:

select array_to_string(array_compact(array_construct( 
          CASE WHEN Red = 'TRUE' THEN 'Red' ELSE NULL  END,
          CASE WHEN Blue = 'TRUE' THEN 'Blue' ELSE NULL END, 
          CASE WHEN Black = 'TRUE' THEN 'Black' ELSE NULL END,
          CASE WHEN White = 'TRUE' THEN 'White' ELSE NULL END)), ', ') as result
FROM values 
( true, true, false, false ),
( true, false, false, true ),
( false, false, true, false ),
( false, true, false, true ),
( true, true, true, true )
v(red,blue,black,white);

EDIT: You can also use array_construct_compact , which is a condensed version of array_construct and array_compact编辑:您还可以使用array_construct_compact ,它是array_constructarray_compact的浓缩版本

You can use RTRIM to remove ending comma:您可以使用 RTRIM 删除结束逗号:

select RTRIM(CONCAT( 
          CASE WHEN Red = 'TRUE' THEN 'Red, ' ELSE ''  END,
          CASE WHEN Blue = 'TRUE' THEN 'Blue, ' ELSE '' END, 
          CASE WHEN Black = 'TRUE' THEN 'Black, ' ELSE '' END,
          CASE WHEN White = 'TRUE' THEN 'White, ' ELSE '' END ),', ' ) result
FROM values 
( true, true, false, false ),
( true, false, false, true ),
( false, false, true, false ),
( false, true, false, true ),
( true, true, true, true )
v(red,blue,black,white);

+-------------------------+
| RESULT                  |
+-------------------------+
| Red, Blue               |
| Red, White              |
| Black                   |
| Blue, White             |
| Red, Blue, Black, White |
+-------------------------+

You may also consider to convert empty string to NULL using NULLIF function:您还可以考虑使用 NULLIF function 将空字符串转换为 NULL:

select NULLIF( RTRIM(CONCAT( 
          CASE WHEN Red = 'TRUE' THEN 'Red, ' ELSE ''  END,
          CASE WHEN Blue = 'TRUE' THEN 'Blue, ' ELSE '' END, 
          CASE WHEN Black = 'TRUE' THEN 'Black, ' ELSE '' END,
          CASE WHEN White = 'TRUE' THEN 'White, ' ELSE '' END ),', ' ), '' )result
FROM values 
( false, false, false, false )
v(red,blue,black,white);

I understand that your expression does quite what you want, but you need to remove the trailing comma.我知道您的表达式完全符合您的要求,但您需要删除结尾的逗号。 You can use TRIM() for this:您可以为此使用TRIM()

TRIM(', ' FROM 
       CASE WHEN Red   = 'TRUE' THEN 'Red, '   ELSE '' END  
    || CASE WHEN Blue  = 'TRUE' THEN 'Blue '   ELSE '' END 
    || CASE WHEN Black = 'TRUE' THEN 'Black, ' ELSE '' END 
    || CASE WHEN White = 'TRUE' THEN 'White, ' ELSE '' END
)

Note that there is no point using both ||请注意,同时使用||是没有意义的。 and CONCAT() : I removed the surrounding CONCAT() .CONCAT() :我删除了周围的CONCAT()

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM