concatenating CASE stmt results

  • Here is what I want to do:

    Select

    , CASE

    when '1' then 'one' else 1 end as ONE

    , CASE

    when '2' then 'two' else 2 end as TWO

    , CASE

    when '3' then 'three' else 3 end as THREE

    , ONE + '' + TWO + '' + THREE AS FinishedNumber

    it is the concatenated result I am struggling with. How do you concatenate CASE results?????????

    thank you in advance!! 😎


    Thank you!!,

    Angelindiego

  • Most important thing first:

    You need to make sure to use the same data type in each part of a CASE statement, otherwise SQL Server will perform an implicit conversion.

    In the sample you provided it'll try to convert 'one' to int since 1 is integer and integer data type has a higher precedence then char/varchar.

    Back to your original question:

    You can concatenate each CASE statement:

    DECLARE @t CHAR(1)

    SET @t='b'

    SELECT

    CASE WHEN @t='a' THEN 'y' ELSE 'n' END

    + CASE WHEN @t>'a' THEN 'o' ELSE 'e' END

    + CASE WHEN @t='b' THEN ' ' ELSE 's' END

    or wrap it into a CTE:

    ;

    ;

    WITH cte as

    (

    SELECT

    CASE WHEN @t='a' THEN 'y' ELSE 'n' END AS ONE,

    CASE WHEN @t>'a' THEN 'o' ELSE 'e' END AS TWO,

    CASE WHEN @t='b' THEN ' ' ELSE 's' END AS THREE

    )

    SELECT ONE + ' ' + TWO + ' ' + THREE

    FROM cte

    But always make sure to have the same data type.



    Lutz
    A pessimist is an optimist with experience.

    How to get fast answers to your question[/url]
    How to post performance related questions[/url]
    Links for Tally Table [/url] , Cross Tabs [/url] and Dynamic Cross Tabs [/url], Delimited Split Function[/url]

  • Couple of things here... It would be helpful if you posted some sample data and expected results as per the first link in my signature. Secondly, It looks like you're taking the character value of '1' and replacing it with text 'one' or if it's not '1' then the integer 1.

    It looks like you're going to have all kinds of explicit conversion issues here, and it makes it somewhat hard to determine how to help.

    Then looking at your case statement itself, you're not showing the expression you are evaluating in any of your case expressions. Here's a link to the BOL (Books online Sql Server's Help Files) Case Syntax for TSQL. I've never liked the shortened version which it looks like you are trying to use because it makes certain things unclear. (I prefer the true boolean expression syntax).

    If I had a table with some text in a column called column one that I needed to evaluate with a Case statement the sample I would provide would look something like this... I've tried to cover a couple of options here because I don't know what you want, see first comment again...

    --do this someplace Safe

    USE TempDB;

    CREATE TABLE #test (

    Col1 VARCHAR(10)

    );

    INSERT INTO #test

    SELECT '1' UNION ALL

    SELECT '2' UNION ALL

    SELECT 'otherstuff' UNION ALL

    SELECT 'one' ;

    --The below gives a datatype conversion error

    --Server: Msg 245, Level 16, State 1, Line 15

    --Syntax error converting the varchar value 'one' to a column of data type int.

    --It's commented out to all the rest to run'

    /*SELECT CASE WHEN col1 = '1' THEN 'one'

    ELSE 1 END AS ONE

    FROM #test; */

    --This resolves it but seems to not be what you want?

    SELECT CASE WHEN col1 = '1' THEN 'one'

    ELSE '1' END AS ONE

    FROM #test;

    --To concat these columns together you need to repeat the statement that created the first column of your resultset

    SELECT CASE WHEN col1 = '1' THEN 'one'

    ELSE '1' END AS ONE,

    --Now I'll Concat another column to the first'

    CASE WHEN col1 = '1' THEN 'one'

    ELSE '1' END + ' ' +

    CASE WHEN col1 = '1' THEN 'one'

    ELSE '1' END AS two

    FROM #test;

    --Cleanup

    DROP TABLE #test;

    Hopefully this will get you in the right direction.

    To help us help you read this[/url]For better help with performance problems please read this[/url]

  • Looks like Lutz beat me to it with a bit better sample code... Not something I would have thought to use a CTE for but it would definitely help with readability, I'll have to keep that in mind for the future.

    and yeah, I meant implicit conversions not explicit πŸ˜‰

    -Luke.

    To help us help you read this[/url]For better help with performance problems please read this[/url]

  • Thank you both SO MUCH for the suggestions!! I am off to make them work!!


    Thank you!!,

    Angelindiego

  • @Angelindiego: Glad we could help!! πŸ˜€

    @luke: πŸ˜› πŸ˜‰

    The CTE stuff came to my mind based on Angelindiegos original post. I usually don't use it either... but it definitely makes troubleshooting easier, especially for concatenation without any separator in between.



    Lutz
    A pessimist is an optimist with experience.

    How to get fast answers to your question[/url]
    How to post performance related questions[/url]
    Links for Tally Table [/url] , Cross Tabs [/url] and Dynamic Cross Tabs [/url], Delimited Split Function[/url]

  • Luke L (9/20/2010)


    I've never liked the shortened version [...] because it makes certain things unclear. (I prefer the true boolean expression syntax).

    What situations do you find unclear? I prefer the short version when possible, because it's clear that all of your comparisons are against the same expression and it's a LOT less typing.

    Drew

    J. Drew Allen
    Business Intelligence Analyst
    Philadelphia, PA

  • It's really a personal preference as AFAIK there's no performance difference, hence the "I prefer to avoid the short version". The longer (searched, or boolean depending on the documentation) version allows the ability to use multiple expressions (which I tend to have to do on a regular basis) and inequality operators rather than just a list of values with equality operators. Also because of this I can be more consistent and I don't have to remember more than one syntax.

    But again, it's personal preference, so use what works for you.

    -Luke.

    To help us help you read this[/url]For better help with performance problems please read this[/url]

  • I don't like the short version at all because it "lies". If you expand the code it actually executes against variables, you find a big surprise. And if you want to do something "tricky", you're in for an even bigger surprise because of the way it actually works in the background...

    For example, you would think that the following would never produce a value of "Unknown" but... guess again...

    SELECT TOP (1000)

    CASE ABS(CHECKSUM(NEWID()))%3 --Produces 0 through 2

    WHEN 0 THEN 'Zero'

    WHEN 1 THEN 'One'

    WHEN 2 THEN 'Two'

    ELSE 'Unknown'

    END

    FROM Master.sys.All_Columns

    Here's the reason why... the scalar operator is actually transformed and the code that actually gets executed looks like the following...

    Scalar Operator(CASE

    WHEN abs(checksum(newid()))%(3)=(0)

    THEN 'Zero'

    ELSE CASE

    WHEN abs(checksum(newid()))%(3)=(1)

    THEN 'One'

    ELSE CASE

    WHEN abs(checksum(newid()))%(3)=(2)

    THEN 'Two'

    ELSE 'Unknown'

    END

    END

    END)

    And that's why the "Unknown" value sometimes happens. The first random generator might not be 0 (could be 1 or 2), the second might not be 1 (could be 0 or 2), and the third might not be 2 (could be 0 or 1). That means that it falls all the way through to the "Unknown" ELSE even though no value was ever produced that wasn't a 0, 1, or 2. πŸ˜›

    Try the same thing with a variable and look at the properties of the Scalar Operator... same thing but you never notice because the WHEN value doesn't change.

    That's why I don't like the shorthand method of CASE.... what you see is NOT what you get. πŸ˜‰

    --Jeff Moden


    RBAR is pronounced "ree-bar" and is a "Modenism" for Row-By-Agonizing-Row.
    First step towards the paradigm shift of writing Set Based code:
    ________Stop thinking about what you want to do to a ROW... think, instead, of what you want to do to a COLUMN.

    Change is inevitable... Change for the better is not.


    Helpful Links:
    How to post code problems
    How to Post Performance Problems
    Create a Tally Function (fnTally)

  • Jeff Moden (9/20/2010)


    I don't like the short version at all because it "lies". If you expand the code it actually executes against variables, you find a big surprise. And if you want to do something "tricky", you're in for an even bigger surprise because of the way it actually works in the background...

    [sic]

    That's why I don't like the shorthand method of CASE.... what you see is NOT what you get. πŸ˜‰

    Apparently there is a performance/code related reason for why I do what I do. Thanks for the correction and the sample code Jeff. Good to start the day learning something new.

    -Luke.

    To help us help you read this[/url]For better help with performance problems please read this[/url]

  • Jeff Moden (9/20/2010)


    I don't like the short version at all because it "lies".

    So a Simple CASE, which on the face of it should work quicker than a Searched CASE because the expression could be evaluated only once, in fact evaluates the expression for each condition. Well I'll be darned. It works the same as a Searched CASE.

    Thanks Jeff, there's another myth busted 😎

    β€œWrite the query the simplest way. If through testing it becomes clear that the performance is inadequate, consider alternative query forms.” - Gail Shaw

    For fast, accurate and documented assistance in answering your questions, please read this article.
    Understanding and using APPLY, (I) and (II) Paul White
    Hidden RBAR: Triangular Joins / The "Numbers" or "Tally" Table: What it is and how it replaces a loop Jeff Moden

  • Jeff Moden (9/20/2010)


    I don't like the short version at all because it "lies".

    That's very interesting, but, realistically, how often do people use nondeterministic functions like NEWID() in the comparison expression of a CASE statement?

    Drew

    J. Drew Allen
    Business Intelligence Analyst
    Philadelphia, PA

  • drew.allen (9/21/2010)


    Jeff Moden (9/20/2010)


    I don't like the short version at all because it "lies".

    That's very interesting, but, realistically, how often do people use nondeterministic functions like NEWID() in the comparison expression of a CASE statement?

    Drew

    I was thinking the same Drew, but what Jeff points out is that Simple and Searched CASE both operate by evaluating the expression for each condition until it "meets true". I've always distinguished between the two types and used Simple CASE where possible on the misunderstanding that it evaluates the condition only once and hence has to be faster. I can feel a test coming on...

    β€œWrite the query the simplest way. If through testing it becomes clear that the performance is inadequate, consider alternative query forms.” - Gail Shaw

    For fast, accurate and documented assistance in answering your questions, please read this article.
    Understanding and using APPLY, (I) and (II) Paul White
    Hidden RBAR: Triangular Joins / The "Numbers" or "Tally" Table: What it is and how it replaces a loop Jeff Moden

  • I don't see how that's a disadvantage of the simple CASE. The complex CASE will have the same issue for the same reason. The first version is still much easier to code and vastly easier to change.

    Scott Pletcher, SQL Server MVP 2008-2010

  • scott.pletcher (9/21/2010)


    I don't see how that's a disadvantage of the simple CASE. The complex CASE will have the same issue for the same reason. The first version is still much easier to code and vastly easier to change.

    It's a disadvantage of Simple CASE because if you are expecting the expression to be evaluated only once, which you'd assume from looking at the code, then you'd be wrong.

    β€œWrite the query the simplest way. If through testing it becomes clear that the performance is inadequate, consider alternative query forms.” - Gail Shaw

    For fast, accurate and documented assistance in answering your questions, please read this article.
    Understanding and using APPLY, (I) and (II) Paul White
    Hidden RBAR: Triangular Joins / The "Numbers" or "Tally" Table: What it is and how it replaces a loop Jeff Moden

Viewing 15 posts - 1 through 15 (of 17 total)

You must be logged in to reply to this topic. Login to reply