web-dev-qa-db-fra.com

Pourquoi une table utiliserait-elle sa clé primaire comme clé étrangère pour elle-même

En parcourant une base de données, je suis tombé sur une table qui utilisait sa clé primaire comme clé étrangère pour elle-même.

J'ai vu qu'une table peut avoir une clé étrangère pour construire une structure de hiérarchie, mais elle utiliserait une autre colonne pour référencer la clé primaire.

Étant donné que la clé primaire est unique, dans cette situation, la ligne ne pourrait-elle pas seulement pointer vers elle-même? Cela semble être un lien tautologique, car si j'ai déjà la ligne, alors j'ai déjà la ligne.

Y a-t-il une raison pour laquelle cela serait fait?

Table joined to itself

Je suis certain que la contrainte est écrite de cette façon (pas seulement en regardant le diagramme) car le même tableau et la même colonne sont utilisés pour les deux moitiés de la définition.

22
Aaroninus

Comme tu as dis. UNE FOREIGN KEY la contrainte référençant la même table correspond généralement à une structure hiérarchique et utilise une autre colonne pour référencer la clé primaire. Un bon exemple est un tableau des employés:

EmployeeId    Int     Primary Key
EmployeeName  String
ManagerId     Int     Foreign key going back to the EmployeeId

Donc, dans ce cas, il y a une clé étrangère de la table sur elle-même. Tous les managers sont également des employés donc le ManagerId est en fait le EmployeeId du manager.

Maintenant, d'un autre côté, si vous voulez dire que quelqu'un a utilisé le EmployeeId comme clé étrangère pour revenir à la table Employee alors c'était probablement une erreur. J'ai fait un test et c'est possible mais ça n'aurait pas vraiment d'utilité.

CREATE TABLE Employee (EmployeeId Int PRIMARY KEY,
                        EmployeeName varchar(50),
                        ManagerId Int);


ALTER TABLE Employee ADD CONSTRAINT fk_employee 
    FOREIGN KEY (EmployeeId) REFERENCES Employee(EmployeeId);
29
Kenneth Fisher

Je viens de trouver une telle clé étrangère dans ma propre base de données et ce doit être moi-même qui l'a créée. Je pense que c'est arrivé par accident. Si je clique sur "Nouvelle clé étrangère" dans le menu contextuel d'une table avec clé primaire (dans Management Studio, SQL 2014 Express), cela crée déjà automatiquement une telle clé étrangère se référant à elle-même. Voir ci-dessous:

enter image description here

Si je ne me rends pas compte que je devrais le modifier au lieu d'en ajouter un nouveau, il y restera. Ou, si je clique simplement sur le bouton [Fermer] ce qui signifie que ce serait comme un [Annuler], la clé étrangère sera toujours créée après avoir enregistré la définition de la table.

Donc, pour moi, une telle clé étrangère n'a aucun sens et peut être supprimée.

6
Stefan Müller

Peut-être que le concepteur a voulu désactiver l'utilisation de TRUNCATE TABLE?

TRUNCATE TABLE ne peut pas être utilisé sur une table avec une contrainte de clé étrangère vers une autre table bien qu'il peut être utilisé s'il y a auto-référentiel clés étrangères. Dans la documentation de TRUNCATE TABLE (Transact-SQL) :

BOL Extract

Une instruction DELETE sans clause WHERE a un effet similaire à une TRUNCATE TABLE (en supprimant toutes les lignes du tableau) mais l'instruction DELETE déclenche la suppression des déclencheurs, ce qui pourrait être une raison pour autoriser DELETE mais pas TRUNCATE TABLE.

Je le ferais en utilisant des autorisations (DELETE nécessite une autorisation de suppression, TRUNCATE TABLE nécessite une autorisation de modification de table), mais il y a peut-être une raison pour laquelle le concepteur n'a pas pu le faire?

Remarque: Même si ce que le concepteur a fait ne désactive pas réellement l'utilisation de TRUNCATE TABLE, Je spécule toujours que c'était leur intention.

4
Greenstone Walker