How to write case condition to check particular value exist among multiple values in sql? - sql

I have a column in table which is having single/multiple value. I have to convert it yes/no based on condition.
example:
rendition_type_sys
distribution
uploaded, distribution
uploaded
single
I need to change the value based on condition. If column having distribution then value should convert as 'Yes' otherwise 'No'
Final Output:
rendition_type_sys
Yes
Yes
No
No
I tried one case statement but that is working for single value not multiple value-
case when ren.rendition_type__sys='distribution' then 'Yes' else 'No' end as rendition_type__sys

First, you should fix your data model so you are not storing multiple values in a string.
In the meantime, like should do what you want. For your example:
(case when ren.rendition_type__sys like '%distribution%'
then 'Yes' else 'No'
end) as rendition_type__sys
Note: In case "distribution" is part of an element name and you don't want that, you can check for delimiters. In Standard SQL, this would be:
(case when ', ' || ren.rendition_type__sys || ', ' like '%, distribution, %'
then 'Yes' else 'No'
end) as rendition_type__sys
The string concatenation operator may vary depending on the database you are using.

This below code would work assuming distribution is not part of any other discrete value; here is the code in a sample form:
WITH rt AS (
SELECT 'distribution' AS rendition_type_sys
UNION SELECT 'uploaded, distribution'
UNION SELECT 'uploaded'
UNION SELECT 'single'
)
SELECT CASE WHEN rt.rendition_type_sys LIKE 'distribution' THEN 'Yes' ELSE 'No' END AS Col
FROM rt
You might consider adding a table with for these "tags" so that they are discrete.

Related

missing right parenthesis when using if

I am trying to use simple IF query in sql developer (Oracle), but i get 'missing right parenthesis' Error. I want to write all ID from my table TEST_TABLE, and write yes if ID is 1234, else 'no'. What am i doing wrong?
select id, if(id = 1234, 'yes', 'no') from TEST_TABLE t
Can't use IF there (IF is for control flow in PLSQL code, not queries), use CASE WHEN instead:
select id, CASE WHEN id = 1234 THEN 'yes' ELSE 'no' END as idIs1234 from TEST_TABLE t
The basic form of a case when is:
CASE
WHEN test THEN truevalue
[WHEN othertest THEN othertruevalue]
[ELSE falsevalue ]
END
CASE must do one or more tests that each return a single value. If no case matches (all tests are false) and there is no ELSE clause, null is returned.
There is also a form that tests a single variable for equality against various values:
CASE id WHEN 1234 THEN 'yes1' WHEN 2345 THEN 'yes2' ELSE 'no' END

Invalid argument for function integer IBM DB2

I need to filter out rows in table where numer_lini column has number in it and it is between 100 and 999, below code works just fine when i comment out line where i cast marsnr to integer. However when i try to use it i get error: Invalid character found in a character string argument of the function "INTEGER". when looking at the list seems like replace and translate filters only numbers just fine and select only contains legit numbers (list of unique values is not long so its easy to scan by eye). So why does it fail to cast something? I also tried using integer(marsnr), but it produces the same error. I need casting because i need numeric range, otherwise i get results like 7,80 and so on. As I mentioned Im using IBM DB2 database.
select numer_lini, war_trasy, id_prz1, id_prz2
from alaska.trasa
where numer_lini in (
select marsnr
from (
select
distinct numer_lini marsnr
from alaska.trasa
where case
when replace(translate(numer_lini, '0','123456789','0'),'0','') = ''
then numer_lini
else 'no'
end <> 'no'
)
where cast(marsnr as integer) between 100 and 999
)
fetch first 300 rows only
If you look at the optimized SQL from the Db2 explain, you will see that Db2 has collapsed your code into a single select.
SELECT DISTINCT Q2.NUMER_LINI AS "NUMER_LINI",
Q2.WAR_TRASY AS "WAR_TRASY",
Q2.ID_PRZ1 AS "ID_PRZ1",
Q2.ID_PRZ2 AS "ID_PRZ2",
Q1.NUMER_LINI
FROM ALASKA.TRASA AS Q1,
ALASKA.TRASA AS Q2
WHERE (Q2.NUMER_LINI = Q1.NUMER_LINI)
AND (100 <= INTEGER(Q1.NUMER_LINI))
AND (INTEGER(Q1.NUMER_LINI) <= 999)
AND (CASE WHEN (REPLACE(TRANSLATE(Q1.NUMER_LINI,
'0',
'123456789',
'0'),
'0',
'') = '') THEN Q1.NUMER_LINI
ELSE 'no' END <> 'no')
Use a CASE to force Db2 to do the "is integer" check first. Also, you don't check for the empty string.
E.g. with this table and data
‪create‬‎ ‪TABLE‬‎ ‪alaska‬‎.‪trasa‬‎ ‪‬‎(‪numer_lini‬‎ ‪VARCHAR‬‎(‪10‬‎)‪‬‎,‪‬‎ ‪war_trasy‬‎ ‪INT‬‎ ‪‬‎,‪‬‎ ‪id_prz1‬‎ ‪INT‬‎,‪‬‎ ‪id_prz2‬‎ ‪INT‬‎)‪;
insert into alaska.trasa values ('',1,1,1),('99',1,1,1),('500',1,1,1),('3000',1,1,1),('00300',1,1,1),('AXS',1,1,1);
This SQL works
select numer_lini, war_trasy, id_prz1, id_prz2
from alaska.trasa
where case when translate(numer_lini, '','0123456789') = ''
and numer_lini <> ''
then integer(numer_lini) else 0 end
between 100 and 999
Although that does fail if there is an embedded space in the input. E.g. '30 0'. To cater for that, a regular expressing is probably preferred. E.g.
select numer_lini, war_trasy, id_prz1, id_prz2
from alaska.trasa
where case when regexp_like(numer_lini, '^\s*[+-]?\s*((\d+\.?\d*)|(\d*\.?\d+))\s*$'))
then integer(numer_lini) else 0 end
between 100 and 999

Using regular expressions in conditional expressions in Postgresql v.9.6

I have a table with a column I denote with "col" containing character values. I would like to extract a column such that at the position where the column "col" starts with either '01', '02' or '03' the column will have the value "yes" and otherwise "no". I tried with the following code and can't get it to work.
SELECT
CASE WHEN col ~ '^(01|02|03)' THEN 'yes'
ELSE 'no' END
FROM table;
I know that one solution is to use the LIKE operator in the following way, but I am looking for a more compact way to solve this.
SELECT
CASE WHEN col LIKE '01%' THEN 'yes'
WHEN col LIKE '02%' THEN 'yes'
WHEN col LIKE '03%' THEN 'yes'
ELSE 'no' END
FROM table;
Any solution, even without regular expression, would be very helpful.
Thanks // Henri

Return 'Yes' or No' from select statement?

tbl_LoanSummary has Sample_Number column. I have to check if Sample_Number column is not null the return 'Y' otherwise return return 'N' from below select statement.
select a.Br_Loan_No ,a.Br_LookupKey, //return IsNull(s.Sample_Number) ='N' or 'Y'
from dbo.tbl_Br a left outer join dbo.tbl_LoanSummary s
on s.Loan_no = a.Br_Loan_No order by a.Br_Loan_No
How to do this?
You can use the case expression for this...
select a.Br_Loan_No,
a.Br_LookupKey,
CASE WHEN s.Sample_Number IS NULL THEN 'N' ELSE 'Y' END AS [HasSample]
from dbo.tbl_Br a left outer join dbo.tbl_LoanSummary s
on s.Loan_no = a.Br_Loan_No order by a.Br_Loan_No
In Oracle, you could also use
select NVL(s.Sample_Number, 'N')
to return N in case of null value
(of course you still need something to have Y in case of not null.)
You'll want to use a CASE expression. It's like an embedded if-statement or switch-statement from traditional programming languages.
SELECT a.Br_Loan_No,
a.Br_LookupKey
CASE
WHEN s.Sample_Number IS NULL THEN 'N'
ELSE 'Y'
END AS sample_number_is_not_null
FROM dbo.tbl_Br a
LEFT JOIN dbo.tbl_LoanSummary s
ON s.Loan_no = a.Br_Loan_No
ORDER BY a.Br_Loan_no
Note that you are creating a computed column here, rather than selecting the raw value of an existing column. It's generally required that you give this column a name, thus the use of the AS sample_number_is_not_null.
There are two forms of the CASE expression. One lets you compare a column or value against several choices. It is like using an implicit equals:
CASE foo
WHEN 3 THEN 'foo is 3!'
WHEN 4 THEN 'foo is 4!'
ELSE 'foo is not 3 or 4'
END
The other form, in the example at the top, lets you use arbitrary expressions in each WHEN clause. It should be noted that each WHEN clause is evaluated in order and the first one to match is the one whose THEN is used as the result. If none of the WHENs match, then the result in the ELSE is used.

Dynamic Label in Select

I was wondering if we can change the label of the select statement like we do for data in sql select using CASE
SELECT CASE column1 = 1 THEN 1 ELSE 0 END AS [Available]
But can we have a dynamic header something like
SELECT column1 AS <-- Available when 1 or Not Available when 0
This can be handled on the front end but its wise if we have it on backend. Any help or useful link is appreciated
You can do it with dynamic sql and if...else instruction but it not make sense for me. In relational database value in the cell tells you if something is available or not. If header tells you the same as cell it's duplicate information. If you want to description of the value you can use case syntax instead of 0/1 value
SELECT CASE when column1 = 1 THEN 'Available'
ELSE 'Not available'
END AS [Available]
Well, that would not make sense, as what would you expect the column name to be if you hade 2 rows, one with 1 (being available) and the other with 0(being Not Available)?
You would have to stick to something like
SELECT
CASE
WHEN column1 = 1
THEN 'Available'
ELSE 'Not available'
END as Availability
FROM YourTable