Bonsoir Paulo,
Je voudrais faire une mise au point suite à ce que j’ai proposé. Revenons à une situation classique, dans laquelle l’attribut k_format est absent de la table TABLEAU :
D’où le code SQL :
CREATE TABLE TYPE_FORMAT
(
k_format AUTOINCREMENT
, libelle_format VARCHAR(32) NOT NULL
, CONSTRAINT TYPE_FORMAT_PK PRIMARY KEY (k_format)
) ;
CREATE TABLE TYPE_CADRE
(
k_cadre AUTOINCREMENT
, reference_cadre VARCHAR(32) NOT NULL
, k_format INT NOT NULL
, CONSTRAINT TYPE_CADRE_PK PRIMARY KEY (k_cadre)
, CONSTRAINT TYPE_CADRE_FORMAT_FK FOREIGN KEY (k_format)
REFERENCES TYPE_FORMAT (k_format)
) ;
CREATE TABLE TYPE_TOILE
(
k_toile AUTOINCREMENT
, type_toile VARCHAR(32) NOT NULL
, k_format INT NOT NULL
, CONSTRAINT TYPE_TOILE_PK PRIMARY KEY (k_toile)
, CONSTRAINT TYPE_TOILE_FORMAT_FK FOREIGN KEY (k_format)
REFERENCES TYPE_FORMAT (k_format)
) ;
CREATE TABLE TABLEAU
(
k_tableau AUTOINCREMENT
, reference_tableau VARCHAR(32) NOT NULL
, k_toile INT NOT NULL
, k_cadre INT NOT NULL
, CONSTRAINT TABLEAU_PK PRIMARY KEY (k_tableau)
, CONSTRAINT TABLEAU_TYPE_TOILE_FK FOREIGN KEY (k_toile)
REFERENCES TYPE_TOILE (k_toile)
, CONSTRAINT TABLEAU_TYPE_CADRE_FK FOREIGN KEY (k_cadre)
REFERENCES TYPE_CADRE (k_cadre)
) ;
Mais dans ces conditions, rien n’empêche qu’un tableau fasse référence à une toile d’un certain format et à un cadre d’un autre format.
L’usage est alors de définir une contrainte interdisant cela. En relationnel pur, on définit cette contrainte ainsi :
CONSTRAINT CT_truc
(TABLEAU JOIN TYPE_CADRE) {k_format, k_tableau} = (TABLEAU JOIN TYPE_TOILE) {k_format, k_tableau} ;
Ce qui se lit : la projection sur les attributs k_format et k_tableau de la jointure (naturelle) des tables TABLEAU et TYPE_CADRE doit être égale à la projection sur ces mêmes attributs de la jointure naturelle des tables TABLEAU et TYPE_TOILE, suite à quoi on peut dormir sur ses deux oreilles, les infractions ne pourront pas se produire. A son tour, la norme SQL prévoit en ce sens une instruction adaptée, à savoir CREATE ASSERTION. Le problème est que les SGBD commercialisés n’implémentent pas cette instruction, on est donc coincés. L’usage est alors de se rabattre sur la mise en oeuvre de triggers, mais ceux-ci sont prévus pour produire plus que pour contrôler. Qui plus est, développer des triggers avec ACCESS ça n’est pas de la tarte, on a plutôt envie de tout envoyer balader...
En conséquence, j’ai proposé une solution dans laquelle on utilise des surclés. Mais attention ! si l’on y regarde de plus près, on constate que la table TABLEAU, dans laquelle est présent l’attribut k_format, est d’une certaine façon délinquante ! En effet, elle enfreint la 3NF (troisième forme normale)... Et tout théoricien, tout professeur frais émoulus s’empresseront de répéter que c’est très mal, il faut « nor-ma-li-ser » ! C'est-à-dire évacuer l’attribut peccamineux k_format de la table TABLEAU. Mais on peut faire une entorse à la théorie : en l’occurrence, les clés étrangères de la table TABLEAU font référence à des surclés, ce qui nous empêche en fait de faire des bêtises tout en enfreignant la 3NF. Ainsi, en relationnel pur ou dans le cadre de la norme SQL, normalisons en 3NF et mettons en oeuvre des contraintes, toutefois, avec les SGBD du marché, utilisons de préférence la solution la plus simple mais avec laquelle la fiabilité n'est en rien sacrifiée.
Partager