Parfois, tu tombes sur des situations où tu dois piger si un ensemble de valeurs est contenu dans un autre, s'ils se croisent, s'ils sont égaux ou si l'un est un sous-ensemble de l'autre. Par exemple :
- Est-ce qu'un utilisateur a accès à certaines catégories ?
- Quels produits ont des tags en commun ?
- Quels tableaux contiennent toutes les valeurs listées ?
Ces trucs-là se gèrent avec les opérateurs de comparaison de tableaux dans PostgreSQL : =, @>, <@ et &&. On va plonger dans chacun de ces opérateurs et voir des exemples concrets.
= — Comparer deux tableaux pour l’égalité
Tu utilises cet opérateur pour checker si deux tableaux sont identiques. La condition renvoie TRUE si les deux tableaux ont la même longueur et exactement les mêmes éléments dans le même ordre.
Exemple :
SELECT ARRAY[1, 2, 3] = ARRAY[1, 2, 3] AS sont_egaux; -- TRUE
SELECT ARRAY[1, 2, 3] = ARRAY[3, 2, 1] AS sont_egaux; -- FALSE
À retenir : l’ordre des éléments compte. Le tableau [1, 2, 3] n’est pas égal à [3, 2, 1].
@> — Un tableau contient un autre tableau
Avec cet opérateur, tu vérifies si un tableau contient tous les éléments d’un autre tableau (peu importe l’ordre). C’est super utile pour checker si tous les éléments recherchés sont présents.
Exemple :
SELECT ARRAY[1, 2, 3] @> ARRAY[1, 2] AS contient; -- TRUE
SELECT ARRAY[1, 2, 3] @> ARRAY[4] AS contient; -- FALSE
Cas pratique : vérifier les droits d’accès. Par exemple, tu veux t’assurer qu’un rôle contient toutes les permissions nécessaires.
<@ — Un tableau est un sous-ensemble d’un autre
C’est l’inverse de l’opérateur @>. Il vérifie si un tableau est entièrement contenu dans un autre.
Exemple :
SELECT ARRAY[1, 2] <@ ARRAY[1, 2, 3] AS est_sous_ensemble; -- TRUE
SELECT ARRAY[4] <@ ARRAY[1, 2, 3] AS est_sous_ensemble; -- FALSE
Cas pratique : quand tu veux checker si une ligne de table a toutes les étiquettes ou catégories nécessaires.
&& — Intersection de tableaux
Cet opérateur vérifie si deux tableaux ont au moins un élément en commun.
Exemple :
SELECT ARRAY[1, 2, 3] && ARRAY[3, 4, 5] AS intersection; -- TRUE
SELECT ARRAY[1, 2, 3] && ARRAY[6, 7, 8] AS intersection; -- FALSE
Cas pratique : trouver des produits ou des enregistrements qui partagent des catégories ou des caractéristiques.
Utiliser les opérateurs pour filtrer des données
Voyons comment utiliser ces opérateurs pour filtrer des données dans une table. Par exemple, on a une table products avec une colonne tags qui contient un tableau de tags pour chaque produit.
Exemple de table products
| id | name | tags |
|---|---|---|
| 1 | "Produit A" | {electronique, promo} |
| 2 | "Produit B" | {maison, promo} |
| 3 | "Produit C" | {electronique, nouveau} |
| 4 | "Produit D" | {maison, jardin} |
On veut trouver tous les produits qui ont le tag electronique.
SELECT *
FROM products
WHERE tags @> ARRAY['electronique'];
Résultat :
| id | name | tags |
|---|---|---|
| 1 | "Produit A" | {electronique, promo} |
| 3 | "Produit C" | {electronique, nouveau} |
On veut trouver les produits dont les tags sont exactement {maison, promo}.
SELECT *
FROM products
WHERE tags = ARRAY['maison', 'promo'];
Résultat :
| id | name | tags |
|---|---|---|
| 2 | "Produit B" | {maison, promo} |
Et maintenant,
trouvons les produits qui ont au moins un des tags {promo, nouveau}.SELECT *
FROM products
WHERE tags && ARRAY['promo', 'nouveau'];
Résultat :
| id | name | tags |
|---|---|---|
| 1 | "Produit A" | {electronique, promo} |
| 2 | "Produit B" | {maison, promo} |
| 3 | "Produit C" | {electronique, nouveau} |
On cherche les produits dont les tags sont strictement limités à {maison, jardin}.
SELECT *
FROM products
WHERE tags <@ ARRAY['maison', 'jardin'];
Résultat :
| id | name | tags |
|---|---|---|
| 4 | "Produit D" | {maison, jardin} |
Exemple : vérifier le contenu des listes avec CASE
On peut combiner la comparaison de tableaux avec des expressions conditionnelles. Par exemple, créons une requête qui marque les produits contenant le tag promo comme "Promo", et les autres comme "Pas de promo" :
SELECT name,
CASE
WHEN tags @> ARRAY['promo'] THEN 'Promo'
ELSE 'Pas de promo'
END AS statut_promo
FROM products;
Résultat :
| name | statut_promo |
|---|---|
| "Produit A" | Promo |
| "Produit B" | Promo |
| "Produit C" | Pas de promo |
| "Produit D" | Pas de promo |
Erreurs courantes et comment les éviter
Erreur : mauvais usage de l’ordre des éléments avec l’opérateur =. Souviens-toi que = exige que l’ordre des éléments soit exactement le même. Si l’ordre n’a pas d’importance, utilise @> ou &&.
Erreur : types de données incompatibles. Les tableaux doivent être du même type. Par exemple, ARRAY['1', '2'] n’est pas égal à ARRAY[1, 2], car le premier est un tableau de chaînes et le second est numérique. Vérifie toujours les types avant de comparer.
Erreur : absence d’index. Si tu filtres souvent des lignes par des tableaux, pense à créer des index (GIN) pour booster les perfs.
Ces opérateurs te permettent de faire du filtrage et de la comparaison de données super puissants, qu’on retrouve tout le temps dans les vrais projets : de l’analyse de tags produits à la gestion des droits d’accès. Si tu les utilises bien, tu vas simplifier des tâches complexes et rendre tes requêtes bien plus efficaces.
GO TO FULL VERSION