Je reviens sur votre interrogation :
Envoyé par
Neelix57
Si un thème T01 a pour ascendant T02 et T03. Comment sait-on que le set recherché fait partie du thème 'T02 > T01' et non du set 'T03 > T01' ?
Un scénario de solution pourrait être le suivant :
Attacher à la table LEGO_SET une table précisant le nom du thème ascendant que l’on souhaite pour le thème référencé par un set donné. Cette table ne concernerait que les sets pour lesquels on aurait besoin d’avoir cette précision. Appelons THEME_ASCENDANT cette table.
Par exemple, dans la table LEGO_SET, le set s09 fait référence au thème T01, et dans la table THEME_ASCENDANT on lui associe son thème ascendant T02 (ça fait un peu thème astrologique...). Ainsi on a le moyen de faire référence à T02 sans faire référence à T03.
Travaux pratiques :
Soit les thèmes suivants :
INSERT INTO THEME (themeId, themeName)
VALUES
(1, 'thème 1'), (2, 'thème 2'), (3, 'thème 3')
, (11, 'thème 11'), (12, 'thème 12'), (13, 'thème 13')
, (14, 'thème 14')
, (20, 'thème 20')
, (120, 'thème 120')
, (130, 'thème 130')
, (1100, 'thème 1100')
, (1200, 'thème 1200')
, (1300, 'thème 1300')
;
Au résultat
SELECT *
FROM THEME
ORDER BY themeId ;
=>
themeId themeName
1 thème 1
2 thème 2
3 thème 3
11 thème 11
12 thème 12
13 thème 13
14 thème 14
20 thème 20
120 thème 120
130 thème 130
1100 thème 1100
1200 thème 1200
1300 thème 1300
Soit La forêt (réseau) TH_TH :
INSERT INTO TH_TH (themeId_enfant, themeId_parent)
VALUES
(1, 11), (1,12), (2, 12)
, (2, 20)
, (12, 120), (13, 120), (13, 130)
, (14, 120)
, (2, 13), (3, 13)
, (120, 1200), (130, 1200)
, (120, 1100), (130, 1300)
;
Au résultat
SELECT themeId_parent, themeId_enfant
FROM TH_TH
ORDER BY themeId_parent DESC ;
=>
themeId_parent themeId_enfant
1300 130
1200 130
1200 120
1100 120
130 13
120 14
120 13
120 12
20 2
13 3
13 2
12 2
12 1
11 1
Le thème qui va nous intéresser est le 'thème 13' qui a pour ascendants les thèmes 'thème 120' et 'thème 130' (en rouge ci-dessus).
Passons au niveau des sets.
Le set 's09' (table LEGO_SET) fait référence au thème 'thème 13' et on voudrait l’associer seulement à son ascendant 'thème 120'.
On déclare la table THEME_ASCENDANT :
CREATE TABLE THEME_ASCENDANT
(
set_num VARCHAR(20) NOT NULL
, themeId_parent INT NOT NULL
, CONSTRAINT THEME_ASCENDANT_PK PRIMARY KEY (set_num)
, constraint THEME_ASCENDANT_LEGO_SET_FK
FOREIGN KEY (set_num)
REFERENCES LEGO_SET (set_num)
, CONSTRAINT THEME_ASCENDANT_THEME_FK
FOREIGN KEY (themeId_parent)
REFERENCES THEME (themeId)
) ;
Insérons une ligne pour le set 's09' :
INSERT INTO THEME_ASCENDANT
SELECT
's09', (SELECT x.themeId
FROM THEME as x
WHERE themeName = 'thème 120'
)
;
Au résultat :
SELECT * FROM THEME_ASCENDANT ;
=>
set_num themeId_parent
s09 120
Pour utiliser les noms des attributs naturels :
SELECT DISTINCT x.set_num, setName
, t.themeName, v.themeName as themeAscendant
FROM LEGO_SET as x
JOIN THEME_ASCENDANT as y ON x.set_num = y.set_num
JOIN TH_TH as z ON x.themeId = z.themeId_parent
JOIN THEME as t ON z.themeId_parent = t.themeId
JOIN TH_TH as u ON y.themeId_parent = u.themeId_parent
JOIN THEME as v ON u.themeId_parent = v.themeId
WHERE x.set_num = 's09'
;
=>
set_num setName themeName themeAscendant
s09 set 9 thème 13 thème 120
Il faudrait bien sûr blinder un peu les contrôles de cohérence, mais il n’y a pas le feu.
Par ailleurs, plus important, le thème ascendant 'thème 120' a lui-même deux ascendants, 'thème 1100' et 'thème 1200', ce qui complique un peu les choses (la forêt devient jungle...). Ce genre de situation existe-t-il pour vous ?
Ce scénario vous convient-il ?
Pour information, mon post Requêtes récursives et son suivant (utiles, car bien likés) pourraient vous apporter des éclairages...
Partager