繁体   English   中英

根据其他三个列的值创建自定义列

[英]Create a custom column based on the values of three other columns

在我目前正在进行的这个项目中(我正在建立一个桌面应用程序和一个新的电子商店之间的桥梁)有一个产品表,其中定义了一些备用列,可以用于最终用户可能需要的任何原因要存储的一些自定义数据。

所以,用户需要设置一个真/假标志来确定产品是否会出现在三个不同的滑块中......不幸的是,实现这一点的人甚至没有使用相同类型的备用列......所以,

  • Slider1 的标志存储在varchar(50)列中
  • Slider2 的标志存储在float列中
  • Slider3 的标志存储在float列中

此外,我为每个SELECT DISTINCT <column>运行了一个SELECT DISTINCT <column>以了解存储在每列中的实际数据,并得到以下结果:

  • varchar列中存储了以下数据:
FLDSTRING1
空值
''
0
1
194276400456
  • float列存储了以下数据:
FLDFLOAT5
空值
0
1
  • 另一个float列有这个:
FLDFLOAT6
空值
1

此外,我运行以下查询以查找为每列存储的数据的不同组合:

SELECT FLDSTRING1, FLDFLOAT5, FLDFLOAT6
FROM MATERIAL
GROUP BY FLDSTRING1, FLDFLOAT5, FLDFLOAT6

并得到以下组合...

FLDSTRING1 FLDFLOAT5 FLDFLOAT6
空值 空值 空值
空值 空值 1
空值 0 空值
空值 1 空值
空值 1 1
'' 空值 空值
'' 空值 1
0 空值 空值
0 0 空值
1 空值 空值
1 空值 1
1 0 空值
1 1 空值
1 1 1
194276400456 0 空值

在所有这些介绍之后我需要什么......

我想要一个像这样的三个逗号分隔值的连接字符串

  • NEWPROD何时FLDSTRING1将评估为true -任何不为NULL,0,或“”
  • CUSTOM1用于FLDFLOAT5评估为true - 基本上是值 1
  • CUSTOM2用于FLDFLOAT6评估为true - 再次值为 1

经过一些试验和错误后,我设法使它达到了某种程度的效果,因为它带来了正确的值,但不是逗号分隔的...

SELECT 
    FLDSTRING1, FLDFLOAT5, FLDFLOAT6, 
    CONCAT(CASE WHEN ISNULL(FLDSTRING1, '') = '' THEN '' ELSE 'NEWPROD' END, 
           CASE WHEN ISNULL(FLDFLOAT5,  '') = '' THEN '' ELSE 'CUSTOM1' END,
           CASE WHEN ISNULL(FLDFLOAT6,  '') = '' THEN '' ELSE 'CUSTOM2' END) AS TAGS
FROM 
    MATERIAL
GROUP BY 
    FLDSTRING1, FLDFLOAT5, FLDFLOAT6;
FLDSTRING1 FLDFLOAT5 FLDFLOAT6 标签
空值 空值 空值
空值 空值 1 自定义2
空值 0 空值
空值 1 空值 自定义1
空值 1 1 自定义1自定义2
'' 空值 空值
'' 空值 1 自定义2
0 空值 空值 新产品
0 0 空值 新产品
1 空值 空值 新产品
1 空值 1 新产品定制2
1 0 空值 新产品
1 1 空值 新产品定制1
1 1 1 NEWPRODCUSTOM1CUSTOM2
194276400456 0 空值 新产品

问题 #1 是我不太明白这是如何工作的......我的意思是,值0不是'' ,但仍然对于NULL 0 NULL的组合我得到一个空值,这就是我想要的......但它是如何做到的?

而且,有人可以更新我的最终查询以逗号分隔计算的TAGS列吗? 问题#2 是我不希望它只包含两个逗号,比如,, ,当组合不能证明三个值中的任何一个出现时......它应该像 PHP 的implode()工作......

为了帮助你帮助我,我包括小提琴与我在这里描述的情景的设置...在此先感谢!

使用CONCAT_WS()函数将值连接到逗号(或其他分隔符)分隔列表中,该列表忽略 nulls

要使用CONCAT_WS() ,如果值为“空白”(根据您的定义),您希望将其传递给真正的NULL ,否则您的自定义标签:

SELECT DISTINCT
  FLDSTRING1,
  FLDFLOAT5,
  FLDFLOAT6,
  CONCAT_WS(',',
    CASE WHEN FLDSTRING1 IS NULL OR FLDSTRING1 = '' OR FLDSTRING1 = '0' THEN NULL ELSE 'NEWPROD' END,
    CASE WHEN FLDFLOAT5 IS NULL OR FLDFLOAT5 = 0 THEN NULL ELSE 'CUSTOM1' END,
    CASE WHEN FLDFLOAT6 IS NULL OR FLDFLOAT6 = 0 THEN NULL ELSE 'CUSTOM2' END) AS TAGS
FROM MATERIAL

DISTINCT替换了GROUP BY因为它更简单并且(在这里)实现了同样的事情。


如果CONCAT_WS不可用:

SELECT DISTINCT
  FLDSTRING1,
  FLDFLOAT5,
  FLDFLOAT6,
  REPLACE(REPLACE(REPLACE(CONCAT(
    CASE WHEN FLDSTRING1 IS NULL OR FLDSTRING1 = '' OR FLDSTRING1 = '0' THEN 'X' ELSE 'NEWPROD' END,
    ',',
    CASE WHEN FLDFLOAT5 IS NULL OR FLDFLOAT5 = 0 THEN 'X' ELSE 'CUSTOM1' END,
    ',',
    CASE WHEN FLDFLOAT6 IS NULL OR FLDFLOAT6 = 0 THEN 'X' ELSE 'CUSTOM2' END
  ), ',X', ''), 'X,', ''), 'X', '') AS TAGS
FROM MATERIAL

dbfiddle

由于您使用的是 SQL Server 2014, CONCAT_WS您可以尝试使用STUFF而不是CONCAT_WS ,如下所示。 通过在所有字符串之前添加分隔符, STUFF将删除找到的第一个逗号。

SELECT 
    FLDSTRING1, 
    FLDFLOAT5, 
    FLDFLOAT6, 
    STUFF(
        CONCAT(
            CASE WHEN FLDSTRING1 IS NULL OR FLDSTRING1 IN ('0','') THEN '' THEN '' ELSE ',NEWPROD' END, 
            CASE WHEN FLDFLOAT5 IS NULL THEN '' ELSE ',CUSTOM1' END,
            CASE WHEN FLDFLOAT6 IS NULL THEN '' ELSE ',CUSTOM2' END
        ),
        1,1,''
    ) AS TAGS
FROM @MATERIAL
GROUP BY FLDSTRING1, FLDFLOAT5, FLDFLOAT6;

查看工作演示数据库小提琴

让我知道这是否适合您。

暂无
暂无

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

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