Je me demandais l'opinion des gens sur la dénomination des colonnes d'identification dans les tables de base de données.
Si j'ai une table appelée Factures avec une clé primaire d'une colonne d'identité, j'appellerais cette colonne InvoiceID afin de ne pas entrer en conflit avec d'autres tables et ce que c'est évident.
Où je travaille actuellement, ils ont appelé toutes les colonnes ID ID.
Donc, ils feraient ce qui suit:
Select
i.ID
, il.ID
From
Invoices i
Left Join InvoiceLines il
on i.ID = il.InvoiceID
Maintenant, je vois quelques problèmes ici:
1. Vous auriez besoin d'aliaser les colonnes sur le select
2. ID = InvoiceID ne rentre pas dans mon cerveau
3. Si vous n'avez pas alias les tables et référé à InvoiceID est-il évident quelle table c'est sur?
Quelles sont les opinions des autres sur le sujet?
Réponses:
ID est un Antipattern SQL. Voir http://www.amazon.com/s/ref=nb_sb_ss_i_1_5?url=search-alias%3Dstripbooks&field-keywords=sql+antipatterns&sprefix=sql+a
Si vous avez de nombreuses tables avec ID comme identifiant, vous rendez les rapports beaucoup plus difficiles. Cela obscurcit le sens et rend les requêtes complexes plus difficiles à lire et vous oblige à utiliser des alias pour vous différencier sur le rapport lui-même.
De plus, si quelqu'un est assez stupide pour utiliser une jointure naturelle dans une base de données où ils sont disponibles, vous vous joindrez aux mauvais enregistrements.
Si vous souhaitez utiliser la syntaxe USING que certaines bases de données autorisent, vous ne le pouvez pas si vous utilisez ID.
Si vous utilisez ID, vous pouvez facilement vous retrouver avec une jointure erronée si vous copiez la syntaxe de jointure (ne me dites pas que personne ne le fait jamais!) Et oubliez de changer l'alias dans la condition de jointure.
Alors tu as maintenant
quand tu voulais dire
Si vous utilisez tablenameID comme champ id, ce type d'erreur accidentelle est beaucoup moins susceptible de se produire et beaucoup plus facile à trouver.
la source
join table2 on table1.table1id = table2.table1id
. Votre raisonnement est correct sauf que si vous utilisez id, le nom de la table est de toute façon devant l'ID.join table2 on table1.id = table2.table1id
... qui est tout aussi verbeux et non redondant, ni oblige des alias obscurs à empêcher la redondance que nous venons de mentionner .. qui à mon avis sont le fléau du développement SQL.Name
champ dans une table, devez-vous le changerTable1Name
pour éviter les mêmes problèmes avec ce champ? Devez-vous préfixer toutes les colonnes avec le nom de la table pour la même raison? Cela ne semble pas juste.J'ai toujours préféré ID à TableName + ID pour la colonne id, puis TableName + ID pour une clé étrangère. De cette façon, toutes les tables ont le même nom pour le champ id et il n'y a pas de description redondante. Cela me semble plus simple car toutes les tables ont le même nom de champ de clé primaire.
Pour ce qui est de joindre des tables et de ne pas savoir quel champ Id appartient à quelle table, à mon avis, la requête devrait être écrite pour gérer cette situation. Là où je travaille, nous préférons toujours les champs que nous utilisons dans une instruction avec l'alias table / table.
la source
Il y a eu un combat de nerd à propos de cette chose même en ma compagnie ces derniers temps. L'avènement de LINQ a rendu le motif redondant de nom de table + ID encore plus évidemment idiot à mes yeux. Je pense que la plupart des gens raisonnables diront que si vous écrivez à la main votre SQL de telle manière que vous devez spécifier les noms de table pour différencier les FK, ce n'est pas seulement une économie de frappe, mais cela ajoute de la clarté à votre SQL à utiliser uniquement l'ID en ce que vous pouvez clairement voir quel est le PK et quel est le FK .
Par exemple
FROM Employés e GAUCHE REJOINDRE Clients c ON e.ID = c.EmployeeID
me dit non seulement que les deux sont liés, mais qui est le PK et qui est le FK . Alors que dans l'ancien style, vous êtes obligé de regarder ou d'espérer qu'ils portent bien leur nom.
la source
Nous utilisons
InvoiceID
, nonID
. Cela rend les requêtes plus lisibles - lorsque vous voyezID
seul, cela peut signifier n'importe quoi, en particulier lorsque vous alias la tablei
.la source
Je suis d'accord avec Keven et quelques autres personnes ici pour dire que le PK d'une table doit simplement être Id et que les clés étrangères listent OtherTable + Id.
Cependant, je souhaite ajouter une raison qui a récemment donné plus de poids à cet argument.
Dans ma position actuelle, nous utilisons le cadre d'entité en utilisant la génération POCO. En utilisant la convention de dénomination standard de l'Id, le PK permet l'héritage d'une classe poco de base avec validation et autres pour les tables qui partagent un ensemble de noms de colonnes communs. L'utilisation de Tablename + Id comme PK pour chacune de ces tables détruit la possibilité d'utiliser une classe de base pour celles-ci.
Seulement un peu de matière à réflexion.
la source
Ma préférence est également ID pour la clé primaire et TableNameID pour la clé étrangère. J'aime aussi avoir une colonne "nom" dans la plupart des tables où je détiens l'identifiant lisible par l'utilisateur (ie nom :-)) de l'entrée. Cette structure offre une grande flexibilité dans l'application elle-même, je peux gérer des tables en masse, de la même manière. C'est une chose très puissante. Habituellement, un logiciel OO est construit au-dessus de la base de données, mais le jeu d'outils OO ne peut pas être appliqué car la base de données elle-même ne le permet pas. Avoir l'identifiant et le nom des colonnes n'est toujours pas très bon, mais c'est une étape.
Pourquoi je ne peux pas faire ça?
À mon avis, c'est très lisible et simple. Nommer les variables comme i et il est un mauvais choix en général.
la source
Ce n'est pas vraiment important, vous risquez de rencontrer des problèmes similaires dans toutes les conventions de dénomination.
Mais il est important d'être cohérent pour ne pas avoir à consulter les définitions de table à chaque fois que vous écrivez une requête.
la source
Je viens de commencer à travailler dans un endroit qui n'utilise que "ID" (dans les tables de base, référencées par TableNameID dans les clés étrangères), et j'ai déjà trouvé DEUX problèmes de production directement causés par celui-ci.
Dans un cas, la requête utilisait "... where ID in (SELECT ID FROM OtherTable ..." au lieu de "... where ID in (SELECT TransID FROM OtherTable ...".
Quelqu'un peut-il honnêtement dire que cela n'aurait pas été beaucoup plus facile à repérer si des noms complets et cohérents avaient été utilisés là où la mauvaise déclaration aurait lu "... where TransID in (SELECT OtherTableID from OtherTable ..."? Je ne pense pas alors.
L'autre problème se produit lors de la refactorisation du code. Si vous utilisez une table temporaire alors qu'auparavant la requête sortait d'une table principale, l'ancien code lit "... dbo.MyFunction (t.ID) ..." et si cela n'est pas modifié mais "t" fait maintenant référence à un table temporaire au lieu de la table principale, vous n'obtenez même pas d'erreur - juste des résultats erronés.
Si générer des erreurs inutiles est un objectif (peut-être que certaines personnes n'ont pas assez de travail?), Alors ce type de convention de dénomination est génial. Sinon, une dénomination cohérente est la voie à suivre.
la source
Par souci de simplicité, la plupart des gens nomment la colonne sur l'ID de table. S'il a une référence de clé étrangère sur une autre table, ils l'appellent explicitement InvoiceID (pour utiliser votre exemple) dans le cas des jointures, vous aliasez la table de toute façon, donc l'inv.ID explicite est toujours plus simple que inv.
la source
Je personnellement préfère (comme il a été indiqué ci - dessus) le Table.ID pour le PK et TableID pour la FK . Même (s'il vous plaît ne me tirez pas dessus) Microsoft Access le recommande.
CEPENDANT, je sais aussi pertinemment que certains outils de génération favorisent le TableID pour PK car ils ont tendance à lier tous les noms de colonnes qui contiennent 'ID' dans le mot, ID INCLUANT !!!
Même le concepteur de requêtes le fait sur Microsoft SQL Server (et pour chaque requête que vous créez, vous finissez par déchirer toutes les relations nouvellement créées inutiles sur toutes les tables sur l'ID de colonne)
AINSI autant que mon OCD interne le déteste, je roule avec la convention TableID . Rappelons-nous que cela s'appelle une base de données , car elle sera la base de nombreuses applications à venir. Et toutes les technologies devraient bénéficier d'un schéma bien normalisé avec une description claire.
Il va sans dire que je trace ma ligne lorsque les gens commencent à utiliser TableName, TableDescription et autres. À mon avis, les conventions devraient faire ce qui suit:
Alias de table: Nom complet de la table, singularisé. Ex.
[Mettre à jour]
En outre, il y a quelques articles valides dans ce fil sur les colonnes dupliquées en raison du "type de relation" ou du rôle. Exemple, si un magasin a un EmployeeID , cela me dit squat. Donc, je fais parfois quelque chose comme Store.EmployeeID_Manager . Bien sûr, c'est un peu plus grand, mais au moins, les gens ne deviendront pas fous en essayant de trouver la table ManagerID , ou ce que EmployeeID y fait. Lorsque la requête est WHERE, je le simplifierais comme: SELECT EmployeeID_Manager comme ManagerID FROM Store
la source
User.UserId
c'est un peu bizarre à taper dans la programmation.En venant à cela du point de vue d'un dictionnaire de données formel, je nommerais l'élément de données
invoice_ID
. En général, un nom d'élément de données sera unique dans le dictionnaire de données et aura idéalement le même nom partout, bien que parfois des termes de qualification supplémentaires puissent être requis en fonction du contexte, par exemple l'élément de données nomméemployee_ID
pourrait être utilisé deux fois dans l'organigramme et donc qualifié commesupervisor_employee_ID
etsubordinate_employee_ID
respectivement.De toute évidence, les conventions de dénomination sont subjectives et une question de style. J'ai trouvé que les directives ISO / CEI 11179 sont un point de départ utile.
Pour le SGBD, je vois les tables comme des collections d'entités (sauf celles qui ne contiennent qu'une seule ligne, par exemple table cofig, table de constantes, etc.), par exemple la table où my
employee_ID
est la clé serait nomméePersonnel
. Donc tout de suite laTableNameID
convention ne fonctionne pas pour moi.J'ai vu le
TableName.ID=PK TableNameID=FK
style utilisé sur les grands modèles de données et je dois dire que je le trouve légèrement déroutant: je préfère de loin que le nom d'un identifiant soit le même partout, c'est-à-dire qu'il ne change pas de nom en fonction de la table dans laquelle il apparaît. le style susmentionné semble être utilisé dans les magasins qui ajoutent uneIDENTITY
colonne (auto-incrémentée) à chaque table tout en évitant les clés naturelles et composées dans les clés étrangères. Ces magasins ont tendance à ne pas avoir de dictionnaires de données formels ni à construire à partir de modèles de données. Encore une fois, ce n'est qu'une question de style et à laquelle je ne souscris pas personnellement. Donc finalement, ce n'est pas pour moi.Cela dit, je peux voir un cas pour parfois supprimer le qualificatif du nom de la colonne lorsque le nom de la table fournit un contexte pour le faire, par exemple l'élément nommé
employee_last_name
peut devenir simplementlast_name
dans laPersonnel
table. La justification ici est que le domaine est `` noms de famille des personnes '' et est plus susceptible d'êtreUNION
édité avec deslast_name
colonnes d' autres tables plutôt que d'être utilisé comme clé étrangère dans une autre table, mais là encore ... je pourrais simplement changer d'avis, parfois on ne peut jamais le dire. C'est la chose: la modélisation des données est en partie un art, en partie une science.la source
Je pense que vous pouvez utiliser n'importe quoi pour "ID" tant que vous êtes cohérent. Il est important d'inclure le nom de la table. Je suggérerais d'utiliser un outil de modélisation comme Erwin pour appliquer les conventions de dénomination et les normes afin que lors de l'écriture de requêtes, il soit facile de comprendre les relations qui peuvent exister entre les tables.
Ce que je veux dire par la première déclaration, c'est qu'au lieu de l'identifiant, vous pouvez utiliser quelque chose d'autre comme «recno». Donc, cette table aurait un PK de facture_recno et ainsi de suite.
Salut, Ben
la source
Mon vote est pour InvoiceID pour l'ID de table. J'utilise également la même convention de dénomination lorsqu'elle est utilisée comme clé étrangère et j'utilise des noms d'alias intelligents dans les requêtes.
Bien sûr, c'est plus long que certains autres exemples. Mais souriez. C'est pour la postérité et un jour, un pauvre codeur junior devra modifier votre chef-d'œuvre. Dans cet exemple, il n'y a pas d'ambiguïté et à mesure que des tables supplémentaires sont ajoutées à la requête, vous serez reconnaissant pour la verbosité.
la source
Pour le nom de la colonne dans la base de données, j'utiliserais "InvoiceID".
Si je copie les champs dans une structure sans nom via LINQ, je peux le nommer «ID» là-bas, si c'est le seul ID de la structure.
Si la colonne ne va PAS être utilisée dans une clé étrangère, afin qu'elle ne soit utilisée que pour identifier de manière unique une ligne pour l'édition ou la suppression, je la nommerai "PK".
la source
Si vous donnez à chaque clé un nom unique, par exemple "factures.invoice_id" au lieu de "factures.id", vous pouvez utiliser les opérateurs "natural join" et "using" sans aucun souci. Par exemple
au lieu de
SQL est assez verbeux sans le rendre plus verbeux.
la source
Ce que je fais pour garder les choses cohérentes pour moi-même (où une table a une seule clé primaire de colonne utilisée comme ID) est de nommer la clé primaire de la table
Table_pk
. Partout où j'ai une clé étrangère pointant vers la clé primaire de cette table, j'appelle la colonnePrimaryKeyTable_fk
. De cette façon, je sais que si j'ai unCustomer_pk
dans ma table Customer et unCustomer_fk
dans ma table Order, je sais que la table Order fait référence à une entrée dans la table Customer.Pour moi, cela a du sens, en particulier pour les jointures où je pense que cela se lit plus facilement.
la source
FWIW, notre nouveau standard (qui change, euh, je veux dire "évolue", à chaque nouveau projet) est:
pk_
préfixe signifie clé primaire_id
suffixe signifie un entier, ID auto-incrémentéfk_
préfixe signifie clé étrangère (pas de suffixe nécessaire)_VW
suffixe pour les vuesis_
préfixe pour les booléensAinsi, une table nommée NAMES peut avoir les champs
pk_name_id, first_name, last_name, is_alive,
etfk_company
et une vue appeléeLIVING_CUSTOMERS_VW
, définis comme:Comme d'autres l'ont dit, cependant, à peu près n'importe quel schéma fonctionnera tant qu'il est cohérent et n'obscurcit pas inutilement vos significations.
la source
Je suis tout à fait d'accord pour inclure le nom de la table dans le nom du champ ID, pour exactement les raisons que vous donnez. Généralement, c'est le seul champ où j'inclurais le nom de la table.
la source
Je déteste le nom d'identité ordinaire. Je préfère fortement toujours utiliser le facture_id ou une variante de celui-ci. Je sais toujours quelle table est la table faisant autorité pour l'identifiant quand j'en ai besoin, mais cela me trouble
Le pire de tout, c'est le mélange que vous mentionnez, totalement déroutant. J'ai dû travailler avec une base de données où presque toujours c'était foo_id sauf dans l'un des identifiants les plus utilisés. C'était un enfer total.
la source
Je préfère DomainName || «ID». (c'est-à-dire DomainName + ID)
DomainName est souvent, mais pas toujours, identique à TableName.
Le problème avec l'ID en soi est qu'il ne s'adapte pas à la hausse. Une fois que vous avez environ 200 tables, chacune avec une première colonne nommée ID, les données commencent à se ressembler. Si vous qualifiez toujours ID avec le nom de la table, cela aide un peu, mais pas tant que ça.
DomainName & ID peuvent être utilisés pour nommer des clés étrangères ainsi que des clés primaires. Lorsque les clés foriegn sont nommées d'après la colonne qu'elles référencent, cela peut être une aide mnémotechnique. Formellement, lier le nom d'une clé étrangère à la clé à laquelle elle fait référence n'est pas nécessaire, puisque la contrainte d'intégrité référentielle établira la référence. Mais c'est extrêmement pratique pour lire les requêtes et les mises à jour.
Parfois, DomainName || «ID» ne peut pas être utilisé, car il y aurait deux colonnes dans la même table avec le même nom. Exemple: Employees.EmployeeID et Employees.SupervisorID. Dans ces cas, j'utilise RoleName || 'ID', comme dans l'exemple.
Enfin, j'utilise des clés naturelles plutôt que des clés synthétiques lorsque cela est possible. Il existe des situations où les clés naturelles ne sont pas disponibles ou ne sont pas dignes de confiance, mais il existe de nombreuses situations où la clé naturelle est le bon choix. Dans ces cas, je laisse la clé naturelle prendre le nom qu'elle aurait naturellement. Ce nom ne contient souvent même pas les lettres «ID». Exemple: OrderNo où No est une abréviation pour "Number".
la source
Pour chaque table, je choisis une abréviation de lettre d'arbre (par exemple, Employés => Emp)
De cette façon, une clé primaire de numérotation automatique numérique devient nkEmp .
Il est court, unique dans toute la base de données et je connais exactement ses propriétés en un coup d'œil.
Je garde les mêmes noms en SQL et dans tous les langages que j'utilise (principalement C #, Javascript, VB6).
la source
Consultez les conventions de dénomination du site Interakt pour un système bien pensé de dénomination des tables et des colonnes. La méthode utilise un suffixe pour chaque table (
_prd
pour une table de produits ou_ctg
pour une table de catégories) et l'ajoute à chaque colonne d'une table donnée. Ainsi, la colonne d'identité de la table products seraitid_prd
et est donc unique dans la base de données.Ils vont un peu plus loin pour aider à comprendre les clés étrangères: la clé étrangère dans la table des produits qui fait référence à la table des catégories serait de
idctg_prd
sorte qu'il soit évident à quelle table elle appartient (_prd
suffixe) et à quelle table elle fait référence (catégorie) .Les avantages sont qu'il n'y a pas d'ambiguïté avec les colonnes d'identité dans différentes tables et que vous pouvez dire en un coup d'œil à quelles colonnes une requête fait référence par les noms de colonne.
la source
voir également la convention de dénomination de clé primaire / clé étrangère
la source
Vous pouvez utiliser la convention de dénomination suivante. Il a ses défauts mais il résout vos problèmes particuliers.
inv
, InvoiceLines -invl
inv_id
-à- direinvl_id
invl_inv_id
pour les noms.de cette façon tu pourrais dire
la source