FirebirdSQL logo

Sous-requêtes liées

Une sous-requête peut être liée (corrélée). Une requête est dite corrélée lorsque la sous-requête et la requête principale sont interdépendantes.Cela signifie que pour chaque enregistrement de la sous-requête à traiter, un enregistrement de la requête principale doit également être récupéré, c’est-à-dire quela sous-requête est entièrement dépendante de la requête principale.

Example 1. Sous-requête liée
SELECT *
FROM Customers C
WHERE EXISTS
      (SELECT *
       FROM Orders O
       WHERE C.cnum = O.cnum
         AND O.adate = DATE '10.03.1990');

Lorsque vous utilisez des sous-requêtes pour récupérer les valeurs des colonnes de sortie dans une liste de sélection SELECT, la sous-requête doit retourner un résultat scalaire.

Sous-requêtes retournant un résultat scalaire

Les Sous-requêtes utilisées dans les prédicats de recherche, à l’exception des prédicats d’existence et de quantité, doivent retourner un résultat scalaire, c’est-à-dire pas plus d’une colonne d’une seule ligne sélectionnée ou une valeur agrégée, sinon une erreur d’exécution (“Multiple rows in a singleton select…​”) se produira.

Note

Bien que Firebird signale une erreur réelle, le message peut être légèrement trompeur.“singleton SELECT” est une requête qui ne doit pas retourner plus d’une chaîne.Cependant, singleton et scalar ne sont pas synonymes : tous les SELECTS à un seul élément ne doivent pas être scalaires ; et un échantillonnage à une seule colonne peut retourner plusieurs lignes pour les prédicats d’existence et de quantité.

Example 1. Sous-requête comme colonne de sortie dans la liste de sélection
SELECT
    e.first_name,
    e.last_name,
    (SELECT
         sh.new_salary
     FROM
         salary_history sh
     WHERE
         sh.emp_no = e.emp_no
     ORDER BY sh.change_date DESC ROWS 1) AS last_salary
FROM
    employee e
Example 2. Sous-requête dans une instruction WHERE pour obtenir la valeur du salaire maximum de l’employé et filtrer par celle-ci.
SELECT
    e.first_name,
    e.last_name,
    e.salary
FROM
    employee e
WHERE
    e.salary = (SELECT
                    MAX(ie.salary)
                FROM
                    employee ie)