C'est une façon d'obtenir le résultat.
Cette approche utilise des sous-requêtes corrélées. Chaque sous-requête utilise un ORDER BY
clause pour trier les lignes liées de table2, et utilise la LIMIT
clause pour récupérer les 1ère, 2ème et 3ème lignes.
SELECT a.PKID
, a.DATA
, (SELECT b1.U_DATA FROM table2 b1
WHERE b1.PKID_FROM_TABLE_1 = a.PKID
ORDER BY b1.U_DATA LIMIT 0,1
) AS U_DATA1
, (SELECT b2.U_DATA FROM table2 b2
WHERE b2.PKID_FROM_TABLE_1 = a.PKID
ORDER BY b2.U_DATA LIMIT 1,1
) AS U_DATA2
, (SELECT b3.U_DATA FROM table2 b3
WHERE b3.PKID_FROM_TABLE_1 = a.PKID
ORDER BY b3.U_DATA LIMIT 2,1
) AS U_DATA3
FROM table1 a
ORDER BY a.PKID
SUIVI
@gliese581g souligne qu'il peut y avoir des problèmes de performances avec cette approche, avec un grand nombre de lignes renvoyées par la requête externe, puisque chaque sous-requête de la liste SELECT est exécutée pour chaque ligne renvoyée dans la requête externe.
Il va sans dire que cette approche nécessite un index :
ON table2 (PKID_FROM_TABLE_1, U_DATA)
-ou, au minimum-
ON table2 (PKID_FROM_TABLE_1)
Il est probable que ce dernier index existe déjà, si une clé étrangère est définie. L'ancien index permettrait de satisfaire entièrement la requête à partir des pages d'index ("Using index"), sans avoir besoin d'une opération de tri ("Using filesort").
@glies581g a tout à fait raison de souligner que les performances de cette approche peuvent être problématiques sur les "grands" ensembles.