Skip to main content

Sargable

Environnement : WINDOWS SQL Server 2012
Base de données : AdventureWorks2012

Définition

Dans les bases de données relationnelles, une condition (ou prédicat) dans une requête est dit être sargable si le moteur SGBD peut profiter d’un index pour accélérer l’exécution de la requête. Le terme est dérivé de la contraction de Search ARGument ABLE.
Une requête à défaut d’être sargable est connu comme requête non – sargable et a un effet sur le temps de recherche, pour l’une des étapes de l’optimisation des requêtes est de les convertir à être sargable.

• Opérateurs Sargable : =,>,<,>=,<=,BETWEEN,LIKE sans % au début,

• Opérateurs non Sargable : <>,IN,OR,NOT IN, NOT EXISTS, NOT LIKE

Exemples de requêtes Sargable

Dans notre exemple, nous allons utiliser la table [Production].[Product] . Et pour démontrer si l’index est utilisé nous observerons le plan d’exécution affiché en mode graphique.

Opérateur logique

SELECT
   [ProductID],
   [Name],
   [rowguid]
FROM
   [Production].[Product]
where
   name = 'Adjustable Race'
or
   rowguid = '694215B7-08F7-4C0D-ACB1-D734BA44C0C8'
Le « or » n'est pas un opérateur ensembliste l'index est balayé entièrement.
Le « or » n’est pas un opérateur ensembliste l’index est balayé entièrement.

Nous allons modifier la requête pour la rendre Sargable en utilisant l’opérateur « Union » :

SELECT
   [ProductID],
   [Name],
   [rowguid]
FROM
   [Production].[Product]
where
   name = 'Adjustable Race'
union all
SELECT
   [ProductID],
   [Name],
   [rowguid]
FROM
   [Production].[Product]
where
   rowguid = '58AE3C20-4F3A-47494749-A7D4-D568806CC537'
L'index est utilisé. Notre requête est Sargable.
L’index est utilisé. Notre requête est Sargable.

Fonction

Pour effectuer le test suivant, nous allons au préalable rajouter un index sur la colonne « SellStartDate ».

CREATE NONCLUSTERED INDEX [ak_product_sellstartdate] ON [Production].[Product]
(
	[SellStartDate] ASC,
	[ProductID] ASC,
	[Name] ASC
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, SORT_IN_TEMPDB = OFF, DROP_EXISTING = OFF, ONLINE = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
GO

Sur cette requête suivante, la colonne est noyée dans une fonction.

SELECT
  [ProductID],
  [Name],
  [SellStartDate]
FROM
  [Production].[Product]
Where
  year(SellStartDate) = 2015

Une fonction dans une "where clause" n'est pas un opérateur ensembliste l'index est balayé entièrement.
Une fonction dans une « where clause » n’est pas un opérateur ensembliste l’index est balayé entièrement.

Nous allons réécrire la requête en utilisant les opérateurs « < » et « > ».

SELECT
  [ProductID],
  [Name]
FROM
  [Production].[Product]
where
  SellStartDate >= '2015-01-01'
And
  SellStartDate < '2016-01-01'
Après modification, nous constatons que notre requête est Sargable, l'index est utilisé
Après modification, nous constatons que notre requête est Sargable, l’index est utilisé

Conclusion

  • Ne pas utiliser de fonction dans une where clause.
  • Évitez les prédicats non – sargable et les remplacer par des équivalents sargable

Vous trouverez d’autres exemples sur notre espace github : exemples sargables

Nicolas C.

Architecte .Net

Laisser un commentaire

Votre adresse e-mail ne sera pas publiée. Les champs obligatoires sont indiqués avec *

Ce site utilise Akismet pour réduire les indésirables. En savoir plus sur comment les données de vos commentaires sont utilisées.