2010-12-15 28 views
17

Tengo una tabla que tiene una columna de valores que puede ser rowTypeID = (1,2,3 o nulo). Me gustaría escribir una consulta que devuelva cualquier fila que no tenga un valor de 3 en ella. En este ejemplo, quiero todas las filas NULL junto con las 1,2 filas. Simplemente no quiero filas con el valor de 3SQL Server return Filas que no son iguales <> a un valor y NULL

Establecer ANSI nulo ON está actualmente configurado para la base de datos.

Soy curioso en cuanto a por qué no puedo escribir

select * from myTable where myCol <> 3 

Esta consulta no devolverá ningún filas que tienen NULL en la columna de la mycol

tengo que escribir

select * from my Table where myCol <> 3 or myCol Is NULL 

¿Siempre tengo que incluir IS NULL o puedo configurarlo para que myCol <> 3 regrese las filas que tienen Null como valor para mi Col

+13

Así funciona NULL, cualquier comparación con él es falsa, excepto IS NULL y NO ES NULO – kurosch

+0

@kurosch: Stricly siguiendo su línea, NULL = NULL también devolvería false, ya que es una comparación? – Marcel

+2

@Marcel: sí, NULL = NULL siempre es falso, y para el caso por lo que es NULL <> NULL :-) – kurosch

Respuesta

14

Creo que su enfoque está bien:

SELECT * 
FROM MyTable 
WHERE myCol <> 3 OR myCol IS NULL 

Puesto que usted está pidiendo alternativas, otra manera de hacerlo es hacer que su columna NOT NULL y guardar otro valor (otherwised sin usar) en la base de datos en lugar de NULL - por ejemplo -1. Entonces, la expresión myCol <> 3 coincidirá con su falso NULL como lo haría con cualquier otro valor.

SELECT * 
FROM MyTable 
WHERE myCol <> 3 

Sin embargo, en general, yo recomendaría no utilizar este método. La forma en que lo estás haciendo es la correcta.

También podría valer la pena mencionar que varias otras bases de datos compatibles con IS DISTINCT FROM que hace exactamente lo que quiere:

SELECT * 
FROM MyTable 
WHERE myCol IS DISTINCT FROM 3 

MySQL tiene la NULL-safe equal que también se pueden utilizar para este propósito:

SELECT * 
FROM MyTable 
WHERE NOT myCol <=> 3 

Lamentablemente, SQL Server aún no admite ninguna de estas sintaxis.

+0

Envíe por favor esta función ISO en el sitio de MS, "DISTINTO PREDICADO": https://connect.microsoft.com/SQLServer/feedback/details/286422/add-language-and-optimizer-support-for-iso-distinct-predicate – montewhizdoh

2

Cada vez que prueba un valor, se omiten todos los valores NULL; después de todo, está comprobando si el valor de alguna columna supera ciertos criterios y NULL es , no es un valor.

3

Debe manejar los NULL de una forma u otra, ya que las expresiones que implican NULLevaluate to Unknown. Si lo desea, en su lugar podría hacer:

select * 
from MyTable 
where isnull(MyColumn, -1) <> 3 

Pero esto implica un número mágico (-1), y que es posiblemente menos legible que la prueba original para IS NULL.

Editar: y, como señala SQLMenace, no es SARGable.

+3

no sargable ... – SQLMenace

+0

seleccione * de MiTabla donde isnull (MiColumna, 3) = 3 – nothrow

+0

@ SQLMenace: buen punto, también tendrá un peor rendimiento: no recomiendo mi sugerencia. – RedFilter

0

porque no se puede comparar a ninguna otra cosa NULL, NULL ni siquiera es igual a NULL

DECLARE @i INT 
DECLARE @i2 INT 

SELECT @i = NULL, @i2 = NULL 

IF @i = @i2 
PRINT 'equal' 
ELSE 
PRINT 'not equal' 
1

qué siempre tengo para incluir el IS NULL o puedo configurarlo para que una cláusula donde myCol <> 3 devolverá las filas que tienen nulo como valor para mi columna?

Usted siempre , siempre, siempre tienen que incluir is null.

Porque 3 no es igual a No/Aplicable y no es igual a Desconocido.

Cuestiones relacionadas