Un método sería el uso de una variante de
WHERE column = nvl(var, column)
Hay dos trampas aquí, sin embargo:
si la columna es anulable, esta cláusula filtrará valores nulos mientras que en su pregunta no filtraría los valores nulos en el segundo caso. Usted puede modificar esta cláusula para tomar en cuenta los valores nulos pero resulta feo:
WHERE nvl(column, impossible_value) = nvl(var, impossible_value)
Por supuesto, si de alguna manera el impossible_value
se inserta cada vez que se ejecutará en algún otro tipo de problemas (FUN).
- El optimizador no entiende correctamente este tipo de cláusula. A veces se generará un plan con UNION ALL, pero si hay más de un par de
nvl
, obtendrá un escaneo completo incluso si hay índices perfectamente válidos.
Por eso, cuando hay un montón de parámetros (varios campos de búsqueda en una gran forma, por ejemplo), me gusta utilizar SQL dinámico:
DECLARE
l_query VARCHAR2(32767) := 'SELECT ... JOIN ... WHERE 1 = 1';
BEGIN
IF param1 IS NOT NULL THEN
l_query := l_query || ' AND column1 = :p1';
ELSE
l_query := l_query || ' AND :p1 IS NULL';
END IF;
/* repeat for each parameter */
...
/* open the cursor dynamically */
OPEN your_ref_cursor FOR l_query USING param1 /*,param2...*/;
END;
También puede utilizar EXECUTE IMMEDIATE l_query INTO l_result USING param1;
Ver una pregunta duplicada y respuestas aquí: http://stackoverflow.com/questions/4042496/how-should-i-deal-with-null-parameters-in-a-pl-sql-stored-procedure-when-i-want –