2017-09-22 10 views
0

Je suis en train de construire un modèle de données pour un nouveau projet que je développe. Une partie de ce modèle de données implique des entités ayant des «drapeaux». Un indicateur est simplement une valeur booléenne - soit une entité a le drapeau, soit elle n'a pas le drapeau. À cette fin, j'ai une table appelée simplement "flags" qui a un ID, un nom de chaîne, et une description. (Par exemple, un utilisateur peut être "actif" ou "doit être affiché" ou "appartient au groupe")Théorie de la base de données: meilleure façon d'avoir une table "flags" qui pourrait s'appliquer à de nombreuses entités?

Ainsi, par exemple, aucun utilisateur de ma table d'utilisateurs ne peut avoir aucun, un ou plusieurs indicateurs. Je crée donc une table de pont userFlags avec l'ID utilisateur et l'identifiant du drapeau. Si la table contient une ligne pour l'ID de drapeau et l'ID utilisateur donnés, cet utilisateur a cet indicateur. Ok, alors maintenant j'ajoute une autre entité - disons "section". Chaque section peut également avoir des drapeaux. Donc, je crée une table sectionFlags pour accueillir cela.

Maintenant, j'ai une autre entité - "contenu", donc encore une fois, "contentFlags".

Et ainsi de suite. Mon modèle de données final comporte essentiellement deux tables par entité, une pour contenir l'entité et une pour les indicateurs.

Bien que ce soit fonctionne, il semble qu'il pourrait y avoir une meilleure façon de concevoir mon modèle, donc je n'ai pas besoin d'avoir autant de tables de pont. Une idée que j'avais était une table principale "hasFlags" avec l'identification de drapeau, l'identification d'article et le type d'article. Le type d'élément peut être un champ énuméré n'acceptant que les valeurs correspondant aux entités connues. Le seul problème est que ma clé étrangère pour l'entité ne fonctionnera pas parce que chaque "ID d'élément" pourrait se référer à une entité différente. (J'ai effectivement utilisé cette technique dans d'autres modèles de données, et bien que cela fonctionne, vous perdez l'intégrité référentielle ainsi que des choses comme les mises à jour en cascade.)

Ou, peut-être que mon modèle de données est bien tel quel et que c'est juste le la nature de la bête.

Les développeurs de bases de données expérimentés les plus avancés sont-ils prêts à intervenir?

Répondre

1

Les relations plusieurs-à-plusieurs sont une façon de le faire (et peut-être plus rapide que ce que je suis sur le point de suggérer car elles peuvent utiliser des index de clés entiers).

L'autre façon de procéder est avec une relation polymorphe.

Votre table d'entité à drapeau nécessite 2 colonnes ainsi que le lien de clé étrangère vers la table de drapeaux;

other_key integer not null 
other_type varchar(...) not null 

Et dans ces domaines que vous stockez la clé étrangère de la relation dans l'entier et le type de la relation dans le varchar. Les ORM full-on qui supportent cela stockent parfois le nom de la classe de la relation étrangère dans la colonne type, pour faciliter le chargement de l'objet. L'inconvénient ici est que l'entier ne peut pas être une vraie clé étrangère car il contiendra des doublons de nombreuses tables. Cela rend également votre requête un peu plus intéressante par jointure que les tables plusieurs-à-plusieurs, mais cela vous permet de généraliser votre jointure de code.