<> and != avoiding NULL in WHERE condition - sql

I have a table PATIENT with Column STATUS. When I queried to get STATUS not equal to 1, I was expecting the result as NULL and 2.
But I am only getting 2 as the result. Can someone help me with this?
CREATE TABLE #PATIENT
(STATUS INT)
INSERT INTO #PATIENT (STATUS)
SELECT 1
UNION
SELECT 2
UNION
SELECT NULL
SELECT * FROM #PATIENT WHERE STATUS <> 1
When I queried with
SELECT * FROM #PATIENT WHERE ISNULL(STATUS, 0) != 1
I am able to get NULL and 2 as the result.
This is SQL SERVER 2012.

You can use OR in WHERE with Condition STATUS IS NULL .
SELECT * FROM #PATIENT WHERE STATUS <> 1 OR STATUS IS NULL
This will do it.
EDIT:
Conceptually, NULL means “a missing unknown value” and it is
treated somewhat differently from other values.
You cannot use arithmetic comparison operators such as =, <, or <>
to test for NULL
Because the result of any arithmetic comparison with NULL is also
NULL, you cannot obtain any meaningful results from such comparisons
we can not equate or not equate anything with null, thats why IS NULL
SELECT NULL <> 1 ===> NULL
Even though it is supposed to be true, it will return `NULL`
Hope this helps.

When you compare NULL value to any value then the result is always NULL.
So if you wan to select the NULL value as well then try this:
SELECT * FROM #PATIENT WHERE STATUS <> 1 OR STATUS IS NULL
DEMO

Conceptually "NULL" means a missing value. To test for NULL IS NULL or IS NOT NULL condition is used. Arithmetic operators cannot be used for comparing NULL values.
NULL<>1 :: returns false because NULL can be 1 or any other value (an unknown value).

Null is a special marker used in Structured Query Language (SQL) to indicate that a data value does not exist in the database.
And reason because you got only 2 and NOT NULL is because in SQL nothing is equal to NULL but also nothing is NOT equal to NULL.
In Simple words you cannot equate and not equate any value with NULL.

Related

what's the difference between is not null and <>' '

Look my example, what's the difference between two codes?
Select name from customers where name is not null
Select name from customers where name <> ''
They do completely different things.
Select name from customers where name is not null
This one selects any customer who has a value in the name field. Those values can include '' as well as things like 'Sam', 'John Jones', 'pretty blonde girl'.
Select name from customers where name <> ''
This will select all names that are not null or blank In Sql Server at least. Other databases may handle this differently. The reason why it also excludes Null is that Null cannot be part of a comparison since it by definition means we don't have a clue what the value of this field is.
If you wanted to return both real names and null values and only exclude the empty strings. In SQl Server you would do:
Select name from customers where coalesce(name, 'Unknown') <>''
There are a lot of correct answers here but I think you are missing what NULL is. It's nothing so it's not comparable to anything. Here's some test for you
DECLARE #param CHAR(1)=NULL --you can replace #param with your column name in your queries
SELECT 1 WHERE #param = NULL --you can't compare NULL to anything using = > < <> != or any other comparision operator
SELECT 1 WHERE #param = '' --an empty value isn't the same as a NULL value so if a NULL is present it won't be returned
SELECT 1 where #param IS NULL --this is how you have to check for null values
--If you want to check for both empty and nulls, you can force the empty string with COALESCE or ISNULL
SELECT 1 WHERE COALESCE(#param,'') = ''
SELECT 1 WHERE ISNULL(#param,'') = ''
The key concept you are missing is that in SQL Server, NULL does not mean no value, it means that the value is unknown. So consider your query with some silly sample data:
DECLARE #t TABLE
( id INT IDENTITY(1,1) PRIMARY KEY CLUSTERED
, name VARCHAR(10) NULL );
INSERT INTO #t
VALUES
('dog'),
('cat'),
(''),
(NULL);
SELECT *
FROM #t
WHERE name <> '';
What you are asking the engine is to return the records where name is not an empty string. On the evaluation of the fourth record, it is determining if NULL equals empty string or not. NULL could be empty string, we don't know ... given that the value is unknown, the engine can't include that record because you are asking for only records where we know the name is definitely not empty string.
Consider another query against the same data:
WITH cteTemp AS
(
SELECT *
, isEqualToEmptyString = CASE WHEN name = '' THEN 'true' ELSE 'false' END
FROM #t
)
SELECT *
FROM cteTemp
WHERE isEqualToEmptyString = 'false';
Now this is written to demonstrate a point and there are cleaner ways to do the same thing (such as the COALESCE in HLGEM's answer.) But understand what is happening here: the query is first determining for sure what names are empty string (which excludes the NULL since its value is unknown) and then excluding those that are. Thus, the NULL is returned.
Null and empty string are two different things. A given field in a table can either have no value (null) or a value of an empty string (''). The results return by each query will be mutually exclusive.
Is not null determines if the object/record being inspected is a true null value or not (no data).
<> '' means is not an empty string, so the record does contain data (that there is an empty string) and is not actually null.
So a query with is not null will return records with a value of string.empty, and a query with <> '' will return values that are neither null nor empty. To catch both empty strings and null values you should use <> '' in your SQL statements.

Select from table with 2 condition and 2 operations

I have a Table BoxTrans
the table Contain Rows (ID,Date,FromBox,ToBox,Value)
I want to make a View like (ID,Date,Box,ValueIn,ValueOut)
select when frombox Give Value to ValueOut
and when tobox Give Value to ValueIN
You can use a CASE statement to check the value of a different column when populating a column. The below query will return your output as long as either ToBox or FromBox is NULL, if they are both not null you may get unexpected results.
SELECT ID,
Date,
COALESCE(ToBox,FromBox) as Box,
CASE WHEN ToBox IS NOT NULL THEN value ELSE NULL as ValueIn,
CASE WHEN FromBox IS NOT NULL THEN value ELSE NULL as ValueOut
FROM BoxTrans

Can a WHERE clause predicate evaluate to NULL?

Can a WHERE clause return NULL instead of TRUE or FALSE?
According to the exercise below it is possible, but i can't imagine an example that returns NULL, Is it really possible?
4. Which of the following values can NOT be returned after evaluation of WHERE clause
condition?
A. UNKNOWN
B. TRUE
C. FALSE
D. NULL
Answer: A. If the result of the condition in WHERE clause is not known, NULL is returned. In all
other scenarios, either TRUE or FALSE is returned.
In SQL, all logical operators evaluate to TRUE, FALSE, and UNKNOWN (Oracle docs) in MySQL UNKNOWN result calls NULL (MySQL docs).
According to oracle documentation:
"To test for nulls, use only the comparison conditions IS NULL and IS
NOT NULL. If you use any other condition with nulls and the result
depends on the value of the null, then the result is UNKNOWN."
So only TRUE, FALSE, and UNKNOWN can be returned after evaluation.
About your question:
"Can a WHERE clause return NULL instead of TRUE or FALSE?"
Strictly speaking in Oracle - NO because the such result called UNKNOWN.
But in general the meaning of UNKNOWN and NULL is equivalent in this context and it is just a different name for the same thing.
So the example of SQL below (a.a >= all) evaluated as UNKNOWN.
with table_a as (
select null as a from dual
union all
select 10 as a from dual
union all
select 5 as a from dual),
table_b as (
select null as a from dual
union all
select 10 as a from dual
union all
select 5 as a from dual)
select * from table_a a where a.a >= all(select a from table_b b)
As to explain the reason, consider that the SQL language uses a three-value logic: TRUE, FALSE, and NULL. Let's consider this Orders table,
If we run the following query it wont return rows for CPU and Monitor
SELECT * FROM Orders WHERE (qty < 1000 Or qty >= 1000)
In this case, for CPU and Monitor condition (qty < 1000 Or qty >= 1000)returns neither TRUE nor FALSE. It returns NULL. Because logically it is unknown. So, the result of the condition in WHERE clause is unknown and it returned NULL.
You can consider this reference.
Not even a NULL can be equal to NULL.
The correct way to understand NULL is that it is not a value. Not
“this is a NULL value” but “this NULL is not a value.” Everything
either is a value, or it isn’t.
When something is a value, it is “1,” or “hello,” or “green,” or
“$5.00″ etc – but when something isn’t a value, it just isn’t
anything at all.
SQL represents “this has no value” by the special non-value NULL.
When someone says “the NULL value,” one should mentally disagree,
because there’s no such thing. NULL is the complete, total absence
of any value whatsoever.
emphasized text
A Non-Technical aspect
If you ask two girls, how old they are? may be you would hear them to
refuse to answer your question, Both girls are giving you NULL as age
and this doesn't mean both have similar age. So there is nothing can
be equal to null.
SELECT 0 IS NULL , 0 IS NOT NULL , '' IS NULL , '' IS NOT NULL, NULL != NULL, NULL = NULL, NULL != '', NULL = ''

Checking tables for null returns 0 regardless

I don't understand why this query doesn't work.
I have a table which is full of rows where 3 of the column values are set to NULL.
But when I run the following query, it returns 0 (it should return 96)
SELECT COUNT(*) FROM SEAT WHERE BOOKED=null;
Do you know what I am doing wrong?
It depends on your database settings and the specific RDBMS you are using, but if you are using ANSI NULL syntax you cannot directly compare a value to NULL with an equality test (=) -- it will always fail.
Use WHERE BOOKED IS NULL instead.
You have to use IS NULL instead of = null
Since null technically isn't a value, you can't compare null using the = operator.
Use IS NULL
SELECT COUNT(*)
FROM SEAT
WHERE BOOKED IS NULL

Trouble comparing smallint in where clause

I have a table with a column called status of type smallint and accepts null. Sql server 2000.
My data contains mostly 2 in that field, but also 0 and null.
When I do
select *
from table
where status <> 2
I don't get all the proper records (where status is null or 0). Any idea why this is happening and how to correct? Shouldn't <> give me everything other than 2?
The NULL test doesn't match any arithmetic comparison.
use
where status <> 2 OR status is null
select *
from table
where ISNULL(status, 1) <> 2
NULL doesn't compare: so remove it.
Your example is the "common mistake" on Wikipedia too...
What you're expecting can be accomplished by setting ANSI_NULLS to off.
For example, try running these queries:
set ansi_nulls off
select case when 1 != null then 'true' else 'false' end
set ansi_nulls on
select case when 1 != null then 'true' else 'false' end
That being said, this is very non-standard SQL behaviour that you're expecting to see. NULL comparisons should always be considered false whether equals to or not equals to comparisons, as every developer will expect that type of SQL query behaviour.
Your WHERE clause should then look like:
where status <> 2 or status is null
Another option would be just to compare to status = 1, if that is the only status that you're expecting to be included in your query.