Question

Je crée une procédure stockée pour renvoyer les résultats de la recherche dans lesquels certains paramètres sont facultatifs.

Je souhaite une déclaration "if" " dans ma clause mais je ne peux pas le faire fonctionner. La clause ne doit filtrer que les paramètres non nuls.

Voici le sp

ALTER PROCEDURE spVillaGet 
-- Add the parameters for the stored procedure here
@accomodationFK int = null,
@regionFK int = null,
@arrivalDate datetime,
@numberOfNights int,
@sleeps int = null,
@priceFloor money = null,
@priceCeil money = null
AS
BEGIN
-- SET NOCOUNT ON added to prevent extra result sets from
-- interfering with SELECT statements.
SET NOCOUNT ON;

-- Insert statements for procedure here
select tblVillas.*, tblWeeklyPrices.price from tblVillas
INNER JOIN tblWeeklyPrices on tblVillas.villaId = tblWeeklyPrices.villaFK
where 
    If @accomodationFK <> null then
        accomodationTypeFK = @accomodationFK 
     @regionFK <> null Then
        And regionFK = @regionFK 
    IF @sleeps <> null Then
        And sleeps = @sleeps 
    IF @priceFloor <> null Then
        And price >= @priceFloor And price <= @priceCeil


END

Des idées comment faire cela?

Était-ce utile?

La solution

select tblVillas.*, tblWeeklyPrices.price 
from tblVillas
INNER JOIN tblWeeklyPrices on tblVillas.villaId = tblWeeklyPrices.villaFK
where (@accomodationFK IS null OR accomodationTypeFK = @accomodationFK)
  AND (@regionFK IS null or regionFK = @regionFK)
  AND (@sleeps IS null OR sleeps = @sleeps)
  AND (@priceFloor IS null OR (price BETWEEN @priceFloor And @priceCeil))

Autres conseils

Nous avons utilisé beaucoup de COALESCE dans le passé pour " clauses WHERE dynamiques " comme vous parlez.

SELECT *
FROM  vehicles
WHERE ([vin]   LIKE COALESCE(@vin, [vin])     + '%' ESCAPE '\')
  AND ([year]  LIKE COALESCE(@year, [year])   + '%' ESCAPE '\')
  AND ([make]  LIKE COALESCE(@make, [make])   + '%' ESCAPE '\')
  AND ([model] LIKE COALESCE(@model, [model]) + '%' ESCAPE '\')

Un gros problème se pose toutefois lorsque vous souhaitez éventuellement filtrer une colonne qui est également nullable ... si les données de la colonne sont null pour une ligne donnée ET si l'utilisateur n'a pas entré Tout élément à rechercher dans cette colonne (la saisie de l'utilisateur est donc également null ), cette ligne n'apparaîtra même pas dans les résultats (ce qui, si vos filtres sont facultatif, est un comportement d'exclusion incorrect).

Afin de compenser les champs nullables, vous devez faire en sorte que le code SQL soit plus compliqué:

SELECT *
FROM  vehicles
WHERE (([vin]   LIKE COALESCE(@vin, [vin])     + '%' ESCAPE '\')
       OR (@vin IS NULL AND [vin] IS NULL))
  AND (([year]  LIKE COALESCE(@year, [year])   + '%' ESCAPE '\')
       OR (@year IS NULL AND [year] IS NULL))
  AND (([make]  LIKE COALESCE(@make, [make])   + '%' ESCAPE '\')
       OR (@make IS NULL AND [make] IS NULL))
  AND (([model] LIKE COALESCE(@model, [model]) + '%' ESCAPE '\')
       OR (@model IS NULL AND [model] IS NULL))

Pour votre compréhension, IF est un code de procédure en T-SQl. Il ne peut pas être utilisé dans une instruction insert / update / delete / select. Il peut uniquement être utilisé pour déterminer laquelle des deux instructions vous souhaitez exécuter. Lorsque vous avez besoin de différentes possibilités dans une instruction, vous pouvez procéder comme ci-dessus ou utiliser une instruction CASE.

Vous pouvez également utiliser la fonction IsNull ou Coalesce

Where accomodationTypeFK = IsNull(@accomodationFK, accomodationTypeFK)
    And regionFK = Coalesce(@regionFK,regionFK)
    And sleeps = IsNull(@sleeps,sleeps ) 
    And price Between IsNull(@priceFloor, Price) And IsNull(priceCeil, Price)  

Cela fait la même chose que la suggestion de Michael ci-dessus ...

IsNull () et Coalesce () fonctionnent plus ou moins de la même manière, ils renvoient le premier argument non-Null de la liste, sauf que iSNull n'autorise que 2 arguments et que Coalesce peut prendre n'importe quel nombre ...

http: / /blogs.msdn.com/sqltips/archive/2008/06/26/differences-between-isnull-and-coalesce.aspx

Essayez de placer votre instruction IF autour de la totalité de l’instruction SQL. Cela signifie qu’il y aura une instruction SQL pour chaque condition. Cela a fonctionné pour moi.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top