简体   繁体   中英

How to concatenate strings and commas in SQL Server?

I'm relatively new to MSSQL, so sorry if the question might sounds trivial. I want to concatenate multiple fields with a delimiter , . However, when the field is empty, the extra , will be included in the result string as well. So is there an easy way to solve this problem? For example,

SELECT VRI.Street_Number_and_Modifier + ',' + 
       VRI.Street_Direction + ',' + 
       VRI.Street_Name + ',' + 
       VRI.Street_Direction + ',' + 
       VRI.Street_Suffix + ',' + 
       VRI.Street_Post_Direction + ',' + 
       VRI.Unit
FROM View_Report_Information_Tables VRI

This modified version of Lamak's handles NULL or strings containing only space/empty:

SELECT  COALESCE(NULLIF(VRI.Street_Number_and_Modifier, '') + ',', '') + 
        COALESCE(NULLIF(VRI.Street_Direction, '') + ',', '') + 
        COALESCE(NULLIF(VRI.Street_Name, '') + ',', '') + 
        COALESCE(NULLIF(VRI.Street_Direction, '') + ',', '') + 
        COALESCE(NULLIF(VRI.Street_Suffix, '') + ',', '') + 
        COALESCE(NULLIF(VRI.Street_Post_Direction, '') + ',', '') + 
        COALESCE(NULLIF(VRI.Unit, ''), '')
FROM View_Report_Information_Tables VRI

I was able to get it to work with a slightly different approach. Putting the commas at the beginning of each field and then removing the first one with the STUFF function worked for me:

SELECT 

    STUFF((COALESCE(', ' + NULLIF(VRI.Street_Number_and_Modifier, ''), '') +
        COALESCE(', ' + NULLIF(VRI.Street_Direction, ''), '') + 
        COALESCE(', ' + NULLIF(VRI.Street_Name, ''), '')) +
        COALESCE(', ' + NULLIF(VRI.Street_Direction, ''), '')) +
        COALESCE(', ' + NULLIF(VRI.Street_Suffix, ''), '')) +
        COALESCE(', ' + NULLIF(VRI.Street_Post_Direction, ''), '')) +
        COALESCE(', ' + NULLIF(VRI.Unit, ''), ''))
    , 1, 2, '')

FROM View_Report_Information_Tables AS VRI

If the columns are empty instead of null, you can try this:

SELECT VRI.Street_Number_and_Modifier 
    + CASE WHEN VRI.Street_Number_and_Modifier <> '' THEN ', ' ELSE '' END
       + VRI.Street_Direction
    + CASE WHEN VRI.Street_Direction <> '' THEN ', ' ELSE '' END
       + VRI.Street_Name
    + CASE WHEN VRI.Street_Name <> '' THEN ', ' ELSE '' END
       + VRI.Street_Direction
    + CASE WHEN VRI.Street_Direction <> '' THEN ', ' ELSE '' END
       + VRI.Street_Suffix
    + CASE WHEN VRI.Street_Suffix <> '' THEN ', ' ELSE '' END
       + VRI.Street_Post_Direction
    + CASE WHEN VRI.Street_Post_Direction <> '' THEN ', ' ELSE '' END
       + VRI.Unit
    + CASE WHEN VRI.Unit<> '' THEN ', ' ELSE '' END
FROM View_Report_Information_Tables VRI

Try this:

SELECT  COALESCE(VRI.Street_Number_and_Modifier + ',','') + 
        COALESCE(VRI.Street_Direction + ',','') + 
        COALESCE(VRI.Street_Name + ',','') + 
        COALESCE(VRI.Street_Direction + ',','') + 
        COALESCE(VRI.Street_Suffix + ',','') + 
        COALESCE(VRI.Street_Post_Direction + ',','') + 
        COALESCE(VRI.Unit,'')
FROM View_Report_Information_Tables VRI

Short or long answer?

Short answer - dont. This is a formatting issue, not a database issue.

Long answer - When you concatenate a string and a null in sql server, the result is null. So you can use combinations of ISNULL

SELECT ISNULL(afield + ',','') + ISNULL(bfield + ',','')

You have to use select case when IsNull(fieldname, '')= '' or ltrim(rtrim(fieldname))='') Then ... Else... end +...

Edit:
Was written from Android mobile.
Below your example.
The following translations (from German) apply, FYI:

Vorname: given name
Name: surname
Benutzer: User

And here's the example code:

CREATE VIEW [dbo].[V_RPT_SEL_Benutzer]  
AS  
SELECT 

    BE_ID AS RPT_UID, 

    CASE 
        WHEN (ISNULL(BE_Name, '0') = '0' OR LTRIM(RTRIM(BE_Name)) = '')  AND (ISNULL(BE_Vorname, '0') = '0' OR LTRIM(RTRIM(BE_Vorname)) = '')
            THEN ''
        WHEN (ISNULL(BE_Name, '0') = '0' OR LTRIM(RTRIM(BE_Name)) = '')
            THEN ISNULL(BE_Vorname, '') 
        WHEN (ISNULL(BE_Vorname, '0') = '0' OR LTRIM(RTRIM(BE_Vorname)) = '')
            THEN ISNULL(BE_Name, '') 
        ELSE
            ISNULL(BE_Name, '') + ', ' + ISNULL(BE_Vorname, '') 
    END AS RPT_Name, 

    ROW_NUMBER() OVER (ORDER BY BE_Name, BE_Vorname ASC) AS RPT_Sort 

FROM T_Benutzer  

For SQL 2008+

Using ISNULL(Colmn1 + ', ', '') Will always result with a leading comma in the end, so you'll have to handle it. Example:

DECLARE @Column1 NVARCHAR(10) = 'Column1'
,   @Column2 NVARCHAR(10) = 'Column2'

SELECT  SUBSTRING(  ISNULL(@Column1 + ', ', '') + ISNULL(@Column2 + ', ', '')
            , 0 --Starting from 0 not 1 to remove leading comma
            , LEN(ISNULL(@Column1 + ', ', '') + ISNULL(@Column2 + ', ', '')))

Or we could approach this the other way around and use the STUFF function to remove our beginning comma which looks cleaner, example:

SELECT  STUFF   (ISNULL(( ', ' + @Column1), '') + ISNULL(( ', ' + @Column2), ''), 1, 2, N'')

For SQL 2012+ we could use the CONCAT function and remove beginning comma using STUFF similar to our previous example but avoiding ISNULL:

SELECT  STUFF(CONCAT( ', ' + @Column1, ', ' + @Column2), 1, 2, N'')

For SQL 2017+ CONCAT_WS was introduced where you can concatinate/join multiple string columns with a delimiter specified in the first argument of the function:

MS Documents CONCAT_WS

MS Doc Example:

SELECT CONCAT_WS(',' --delimiter
            ,'1 Microsoft Way', NULL, NULL, 'Redmond', 'WA', 98052) AS Address;
SELECT  COALESCE(NULLIF(ad.UDEFPROPERTYADDRESS_ADDRSS_LN_1_TXT, ''), ',')+
    COALESCE(NULLIF(ad.UDEFPROPERTYADDRESS_ADDRSS_LN_2_TXT, '') , ',')+
    COALESCE(NULLIF(ad.UDEFPROPERTYADDRESS_ADDRSS_LN_3_TXT, '') , ',')+
    COALESCE(NULLIF(ad.UDEFPROPERTYADDRESS_CITY_TXT, '') , ',')+
    COALESCE(NULLIF(ad.UDEFPROPERTYADDRESS_ST_TXT, '') , ',')+
    COALESCE(NULLIF(ad.UDEFPROPERTYADDRESS_CNTRY_TXT, '') , ',')+
    COALESCE(NULLIF(ad.UDEFPROPERTYADDRESS_PSTL_CD, '') , '')
    FROM ACCOUNT_DETAILS ad

您可以使用ISNULL(field + ',', '')

SELECT isnull(VRI.Street_Number_and_Modifier + ',','')+
   isnull(VRI.Street_Direction + ',','')+
   isnull(VRI.Street_Name + ',','')+
   isnull(VRI.Street_Direction + ',','')+
   isnull(VRI.Street_Suffix + ',','')+
   isnull(VRI.Street_Post_Direction + ',','')+
   isnull(VRI.Unit,'')
FROM View_Report_Information_Tables VRI

I would agree completely with Jamiec's short answer.

Otherwise, I would look at a nasty solution of using a REPLACE([concat], ',,', ',') everywhere you concatenate two columns, and then figure out how to trim commas from the beginning and end of the string where the first and last columns might be empty. Very very messy.

Wanted to see if I can get it without using CASE but could not. A long-winded way of mine:

    SELECT case when isnull(nullif(VRI.Street_Number_and_Modifier, ''),'')='' then '' else VRI.Street_Number_and_Modifier end
+ case when isnull(nullif(VRI.Street_Direction, ''),'')='' then '' else ',' + VRI.Street_Direction end
+ case when isnull(nullif(VRI.Street_Name, ''),'')='' then '' else ',' + VRI.Street_Name end
+ case when isnull(nullif(VRI.Street_Suffix, ''),'')='' then '' else ',' + VRI.Street_Suffix end
+ case when isnull(nullif(VRI.Street_Post_Direction, ''),'')='' then '' else ',' + VRI.Street_Post_Direction end
+ case when isnull(nullif(VRI.Street_Post_Direction, ''),'')='' then '' else ',' + VRI.Street_Post_Direction end
FROM View_Report_Information_Tables VRI

This will not add any commas if null-strings

SELECT CONCAT_WS(', ', IFNULL(column1, NULL), 
         IFNULL(column2, NULL), IFNULL(column3, NULL), 
         IFNULL(column4, NULL), IFNULL(column5, NULL))
FROM yourtable

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

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