Below is my where condition in query
WHERE ResetID= CASE WHEN NOT EXISTS (select 1 FROM ops.table where LabelItemId=#Item) THEN NULL
WHEN #LastIssued < #LastDispatched THEN 1
WHEN #LastIssued >= #LastDispatched THEN 2
END
If case statement returns null the where condition will not work.. Any alternate solution for this condition without case
If you want to have NULL = NULL, you need to handle it with IS NULL. At a guess, what you want is this:
WHERE (ResetID = CASE WHEN NOT EXISTS (select 1 FROM ops.table where LabelItemId=#Item) THEN NULL
WHEN #LastIssued < #LastDispatched THEN 1
WHEN #LastIssued >= #LastDispatched THEN 2
END
OR (ResetID IS NULL AND NOT EXISTS (select 1 FROM ops.table where LabelItemId=#Item)))
Edit note that this does require 2 scans of the table ops.table; there may be a better way to do this, but difficult to suggest when we only have a snippet.
Related
Can someone please explain to me in laymen terms why do we put ISNULL? I have an understanding of IS NULL but can't seem to put it together in this CASE context and what would be the impact if you didn't put it.
UpdateTime refers to when a particular row has been updated with new information
Example 1:
CASE WHEN ISNULL(DB1.UpdateTime,'') >= ISNULL(DB2.UpdateTime,'') THEN ISNULL(DB1.UpdateTime,'')
ELSE DB2.UpdateTime
END AS UpdateTime
FROM dbo.DB1_Result DB1 INNER JOIN dbo.DB2 DB2
ON DB1.ID = DB2.ID
Example 2:
StartTime = 01/01/2022
WHERE
(ISNULL(DB1.UpdateTime,'') >= #StartTime
Thank you!
SQL uses trinary logic: true, false, and null. null means the value is unknown, it could be anything.
If you try to compare anything with null you get null, even null. null = anything is null. null <> anything is null. null < anything is null. null > anything is also null.
Null is neither equal nor not equal to itself. null = null is null and null <> null is null. This is why we write x is null not x = null.
If you were to write
case
when DB1.UpdateTime >= DB2.UpdateTime then
db1.UpdateTime
else
db2.UpdateTime
end
and if either one is null the DB1.UpdateTime >= DB2.UpdateTime will be null. Case will treat that as false and return DB2.UpdateTime. If either value is null, you always get DB2.UpdateTime even if it's null and DB1.UpdateTime is not.
They don't want that. If DB2.UpdateTime is null, they want to return DB1.UpdateTime. If DB1.UpdateTime is null, they want to return DB2.UpdateTime. So they've used isnull to convert null to something that will compare as less than any time; '' works for that.
Demonstration.
Note: ELSE DB2.UpdateTime may want to be ELSE isnull(DB2.UpdateTime, '') to be consistent with THEN ISNULL(DB1.UpdateTime,'').
Note: isnull is a SQL Server extension. The SQL standard is coalesce.
Note: '' is not a timestamp. It happens to work, but other SQL servers will reject it. 1900-01-01 would be better.
How can I return IS NOT NULL on from a SQL Server CASE statement?
I have tried something like this:
WHERE
a.BillToCustomerID IS NOT NULL
AND CASE #taxSchedRequiered
WHEN 1 THEN a.TaxScheduleID IS NOT NULL
END
but it is not working for me.
Update
I need to filter by a.TaxScheduleID IS NOT NULL, just in the specific case when the value of the variable #taxSchedRequiered (possible values are: null, 0, 1) is 1.
just change the logic and use an OR
WHERE
a.BillToCustomerID IS NOT NULL
AND (#taxSchedRequiered <> 1 OR a.TaxScheduleID IS NOT NULL)
this will include all records if #taxSchedRequiered = 0 else it will only include records that have a a.TaxScheduleID <> NULL
Also make sure that #taxSchedRequired has a value other than NULL when you execute this
Edit to check for null param
WHERE
a.BillToCustomerID IS NOT NULL
AND (ISNULL(#taxSchedRequiered,0) = 0 OR a.TaxScheduleID IS NOT NULL)
I'm trying to run the following case statement in SQL:
CASE
WHEN P.Photos_Cloned_From IS NULL
THEN 'http://www.toolboxbarn.com/v/vspfiles/photos/'+P.ProductCode+'-2T.jpg'
ELSE 'http://www.toolboxbarn.com/v/vspfiles/photos/'+P.Photos_Cloned_From+'-2T.jpg'
END AS image_link,
The statements works, but only for those records that are not NULL. For items that are NULL, the statement is not returning the THEN condition.
Any suggestions?
Try this and let us know what happens.
'http://www.toolboxbarn.com/v/vspfiles/photos/'+
COALESCE(P.Photos_Cloned_From,P.ProductCode,'DEFAULT')+'-2T.jpg'
AS image_link,
Using coalesce here is better than the case statement. Some platforms can optimize coalesce and it lets you easily make a default value.
#hogan's Suggestion is a great one to save code, but ultimately it should have the same result as your case statement if you don't introduce his new 'default' case. It is most likely that the ProductCode is also NULL is that a possibility?
Why string + NULL = NULL because NULL is an unknown in sql most db platforms will nullify the entire value when null is aggregated or concatenated.
So Think of the following test cases:
Id ProductCode Photos_Cloned_From
1 1 ClonedFrom
2 2 Null
3 NULL Null
The results of your case expression and Hogan's Suggestion would be:
1) ELSE 'http://www.toolboxbarn.com/v/vspfiles/photos/ClonedFrom-2T.jpg'
2) WHEN 'http://www.toolboxbarn.com/v/vspfiles/photos/2-2T.jpg'
3) WHEN NULL
CASE WHEN ISNULL(P.Photos_Cloned_From,'') = '' THEN 'http://www.toolboxbarn.com/v/vspfiles/photos/'+P.ProductCode+'-2T.jpg'
ELSE 'http://www.toolboxbarn.com/v/vspfiles/photos/'+P.Photos_Cloned_From+'-2T.jpg'
END AS image_link,
SELECT
F.Name
, F.Address
, F.InDate
, ( CASE WHEN (F.Date_Down IS NULL and F.Cod_Down = 0 )THEN 0 ELSE -1 END) as 'sn_Down'
FROM
Folders F
I have a big stored procedure, and basically I want to select all values (including null) if my variable #DimBrowserId is set to 0. I am using a case statement, however this is only catching values that actually have something and ignoring the NULL valued fields. Because I am using the = clause in the WHERE I cannot do IS NULL. I do not want to have to write 2 IF statements because the stored procedure would then be enormous, so I want to know how to get null values as well. Here is my code:
SELECT
DATEPART(yy, DATEADD(mi, #Mdelta, d.DimDateValue)),
DisableCount = COUNT(*)
FROM
dbo.FactDisable AS f
JOIN
dbo.DimDate AS d ON f.DimDateId = d.DimDateId
JOIN
dbo.DimDevice AS v ON f.DimDeviceId = v.DimDeviceId
WHERE
d.DimDateValue >= #StartDateGMT
AND d.DimDateValue <= #EndDateGMT
AND f.IsTest = #IncludeTest
AND f.DimProductId = #DimProductId
AND v.DimBrowserId = CASE
WHEN #DimBrowserId = 0 THEN v.DimBrowserId
ELSE #DimBrowserId
END
GROUP BY
DATEPART(yy, DATEADD(mi, #Mdelta, d.DimDateValue))
The code is near the CASE clause.
Thanks
Change that line to be
AND (#DimBrowserID = 0 OR #DimBrowserID = v.DimBrowserId)
If #DimBroserID is 0 then no filtering will be applied for this line.
Use ISNULL:
SELECT DATEPART(yy,DATEADD(mi,#Mdelta,d.DimDateValue)),
DisableCount=COUNT(*)
FROM dbo.FactDisable AS f
JOIN dbo.DimDate AS d ON f.DimDateId = d.DimDateId
JOIN dbo.DimDevice AS v ON f.DimDeviceId = v.DimDeviceId
WHERE d.DimDateValue >= #StartDateGMT AND d.DimDateValue <= #EndDateGMT
AND f.IsTest = #IncludeTest AND f.DimProductId = #DimProductId
AND v.DimBrowserId = CASE WHEN ISNULL(#DimBrowserId,0) = 0 THEN v.DimBrowserId ELSE #DimBrowserId END
GROUP BY DATEPART(yy,DATEADD(mi,#Mdelta,d.DimDateValue))
CASE WHEN COALESCE(#MightBeNull, 0) = 0 THEN ZeroResult ...
will be treated as zero if #MightBeNull is null, and whatever #MightBeNull is if it's not null.
Assuming null means any browser, a better data model for this scenario might be to set an ID that identifies any browser, instead of setting it to null.
You probably know what you are running into is NULL does not equal NULL in a comparison.
Assuming you don't have control of the data model to fix that, one option would be to coalesce your NULL values to an unused id.
The resulting WHERE clause would look like this, assuming -1 is the unused value you choose.
AND COALESCE(v.DimBrowserId, -1) = CASE WHEN #DimBrowserId = 0 THEN COALESCE(v.DimBrowserId, -1) ELSE #DimBrowserId END
I'm beating my head against the wall here... can't figure out a way to pull this off.
Here's my setup:
My table has a column for the date something was completed. If it was never completed, the field is null. Simple enough.
On the front end, I have a checkbox that defaults to "Only show incomplete entries". When only pulling incomplete entries, it's easy.
SELECT
*
FROM Sometable
WHERE Completed_Date IS NULL
But offering the checkbox option complicates things a great deal. My checkbox inputs a bit value: 1=only show incomplete, 0=show all.
The problem is, I can't use a CASE statement within the where clause, because an actual value uses "=" to compare, and checking null uses "IS". For example:
SELECT
*
FROM Sometable
WHERE Completed_Date IS <---- invalid syntax
CASE WHEN
...
END
SELECT
*
FROM Sometable
WHERE Completed_Date =
CASE WHEN #OnlyIncomplete = 1 THEN
NULL <----- this translates to "WHERE Completed_Date = NULL", which won't work.. I have to use "IS NULL"
...
END
Any idea how to accomplish this seemly easy task? I'm stumped... thanks.
...
WHERE #OnlyIncomplete = 0
OR (#OnlyIncomplete = 1 AND Completed_Date IS NULL)
Hmmm... I think what you want is this:
SELECT
*
FROM Sometable
WHERE Completed_Date IS NULL OR (#OnlyIncomplete = 0)
So that'll show Date=NULL plus, if OnlyIncomplete=0, Date != Null. Yeah, I think that's it.
If you still want to use a CASE function (although it may be overkill in this case) :
SELECT
*
FROM Sometable
WHERE 1 =
(CASE WHEN #OnlyIncomplete = 0 THEN 1
WHEN #OnlyIncomplete = 1 AND Completed_Date IS NULL THEN 1
END)