Comment concevoir une table de produits pour de nombreux types de produit où chaque produit a de nombreux paramètres
Je n'ai pas beaucoup d'expérience dans la conception d'une table. Mon but est de créer une ou plusieurs tables de produits qui répondent aux exigences ci-dessous:
-
En charge de nombreux types de produits (TV, Téléphone, PC, ...). Chaque type de produit a un autre ensemble de paramètres, comme:
-
Téléphone aura la Couleur, la Taille, le Poids, OS...
-
PC aura CPU, HDD, RAM...
-
-
Le jeu de paramètres doit être dynamique. Vous pouvez ajouter ou modifier n'importe quel paramètre que vous souhaitez.
Comment puis-je répondre à ces exigences sans un tableau distinct pour chaque type de produit?
Vous devez vous connecter pour publier un commentaire.
Vous avez au moins cinq options pour la modélisation de la hiérarchie du type que vous décrivez:
Seul L'Héritage De Table: une table pour tous les types de Produits, avec assez de colonnes pour stocker tous les attributs de tous les types. Cela signifie beaucoup de colonnes, dont la plupart sont NULLES sur une ligne donnée.
La Classe De L'Héritage De Table: un tableau pour les Produits, le stockage des attributs communs à tous les types de produits. Puis une table par type de produit, le stockage des attributs spécifiques à ce type de produit.
Le Béton De L'Héritage De Table: pas de table pour le commun des caractéristiques des Produits. Au lieu de cela, un tableau pour chaque type de produit, le stockage commun les attributs d'un produit, le produit, les attributs spécifiques.
Sérialisé LOB: Un tableau pour les Produits, le stockage des attributs communs à tous les types de produits. Une colonne supplémentaire magasins une GOUTTE de données semi-structurées en XML, YAML, JSON, ou tout autre format. Ce BLOB permet de stocker les attributs spécifiques à chaque type de produit. Vous pouvez utiliser la Conception de fantaisie Schémas de le décrire, comme la Façade et le Souvenir. Mais peu importe, vous avez une goutte d'attributs qui ne peuvent pas facilement être interrogés dans SQL; vous devez chercher de l'ensemble de blob revenir à l'application et de faire le tri là.
Entité-Attribut-Valeur: Un tableau pour les Produits, et une table qui pivote attributs de lignes, au lieu de colonnes. La VAE est pas valide à l'égard du paradigme relationnel, mais beaucoup de gens l'utiliser de toute façon. C'est la "Propriétés du Modèle" mentionné par une autre réponse. Voir les autres questions avec le eav tag sur StackOverflow pour certains pièges.
J'ai écrit plus à ce sujet dans une présentation, Extensible De Modélisation De Données.
Réflexions supplémentaires sur la VAE: Bien que beaucoup de gens semblent privilégier la VAE, je n'ai pas. Il semble que la solution la plus souple, et donc le meilleur. Cependant, gardez à l'esprit l'adage TANSTAAFL. Voici quelques-uns des inconvénients de VAE:
NOT NULL
).JOIN
pour chaque attribut.Le degré de flexibilité EAV vous donne exige des sacrifices dans d'autres domaines, probablement rendre votre code aussi complexe (ou pire) qu'il aurait été à résoudre le problème de manière plus conventionnelle.
Et dans la plupart des cas, il est inutile d'avoir un degré de flexibilité. Dans le cas des OP question sur les types de produits, il est beaucoup plus simple de créer une table par type de produit pour le produit attributs spécifiques, si vous avez une structure cohérente appliquée, du moins pour les inscriptions du même type de produit.
J'utiliserais EAV seulement si chaque ligne doivent être autorisés à potentiellement avoir un ensemble distinct de qualités. Lorsque vous avez un ensemble fini de types de produits, la VAE est exagéré. La classe de l'Héritage de Table serait mon premier choix.
Mise à jour 2019: plus je vois les gens en utilisant JSON comme une solution pour les "nombreux attributs personnalisés" problème, du moins j'aime à cette solution. Il fait des requêtes trop complexe, même lors de l'utilisation de spécial JSON fonctions pour les soutenir. Il faut beaucoup plus d'espace de stockage pour stocker des documents JSON, par rapport à ranger dans la normale des lignes et des colonnes.
Fondamentalement, aucune de ces solutions sont faciles et les plus efficaces dans une base de données relationnelle. L'idée d'avoir une "variable d'attributs" est fondamentalement en contradiction avec la théorie relationnelle.
Ce que c'est que vous devez choisir l'une des solutions basées sur ce qui est le moins mauvais pour votre app. Par conséquent, vous devez savoir comment vous allez interroger les données avant de choisir une conception de base de données. Il n'y a pas moyen de choisir une solution qui est "meilleur", car une des solutions pourrait être le meilleur pour une application donnée.
NOT NULL
mais vous pouvez utiliser d'autres contraintes. De cette façon, des IST et de la CTI sont mieux que d'utiliser VAE ou JSON.@StoneHeart
Je voudrais aller ici avec EAV et MVC tout le chemin.
@Bill Karvin
Toutes ces choses que vous avez mentionnées ici:
à mon avis n'a pas sa place dans une base de données à tous les car aucun des bases de données sont capables de gérer ces interactions et les exigences à un niveau convenable en tant que langage de programmation d'une application.
À mon avis, à l'aide d'une base de données de cette façon, c'est comme utiliser une pierre marteau d'un ongle. Vous pouvez le faire avec une pierre, mais n'est-ce pas supposer à utiliser un marteau qui est plus précise et plus spécifiquement conçu pour ce genre d'activité ?
Ce problème peut être résolu en faisant quelques requêtes sur des données partielles et de leur transformation en tabulaire avec votre application. Même si vous disposez de 600 GO de données sur les produits, vous pouvez les traiter en lots si vous avez besoin de données à partir de chaque ligne dans cette table.
D'aller plus loin Si vous souhaitez améliorer les performances des requêtes, vous pouvez sélectionner certaines opérations, comme par exemple, de reporting ou de texte global de la recherche et de préparer leur indice de tables qui serait de stocker les données nécessaires et serait régénéré périodiquement, par exemple toutes les 30 minutes.
Vous n'avez même pas besoin d'être préoccupés par le coût supplémentaire de stockage de données car il est moins cher et moins cher tous les jours.
Si vous continuez d'être concerné par les performances des opérations effectuées par l'application, vous pouvez toujours utiliser Erlang, C++, Langage Go pour pré-traiter les données et, plus tard, sur le processus de l'optimisation des données dans votre application principale.
you can always use Erlang, C++, Go Language to pre-process the data
Que vouliez-vous dire? Au lieu de DB, l'utilisation d'Aller lang? Pourriez-vous veuillez donner des détails sur qui?Si j'utilise
Class Table Inheritance
sens:Que j'aime le mieux au projet de Loi Karwin Suggestions.. je peux prévoir un inconvénient, je vais essayer d'expliquer comment éviter de devenir un problème.
Ce plan d'urgence doit, j'ai de la place quand un attribut qui est seulement commun de type 1, puis devient commune à 2, puis 3, etc?
Par exemple: (c'est juste un exemple, pas mon vrai problème)
Si nous vendre des meubles, nous pouvons vendre des chaises, des lampes, canapés, Télévision, etc. Le type de TÉLÉVISEUR peut être le seul type que nous portons qui a une consommation d'énergie. Donc, je voudrais mettre l'
power_consumption
attribut sur latv_type_table
. Mais alors nous commençons à réaliser des systèmes de cinéma Maison, qui ont aussi unpower_consumption
de la propriété. OK c'est juste l'un des autres produits donc je vais ajouter ce champ dans lestereo_type_table
ainsi puisque c'est probablement la plus simple à ce point. Mais avec le temps que nous commençons à réaliser de plus en plus et de l'électronique, nous nous rendons compte quepower_consumption
est assez large qu'il devrait être dans lemain_product_table
. Que dois-je faire maintenant?Ajouter le champ à la
main_product_table
. Écrire un script pour faire une boucle par le biais de l'électronique et de mettre la bonne valeur de chaquetype_table
à lamain_product_table
. Puis déposez la colonne de chaquetype_table
.Maintenant, Si j'ai été en utilisant toujours le même
GetProductData
classe d'interagir avec la base de données pour tirer des informations sur les produits; ainsi, si des changements dans le code maintenant besoin de refactoring, ils doivent être de la Classe seulement.Vous pouvez avoir une table de Produit et un autre ProductAdditionInfo tableau avec 3 colonnes: ID de produit, pour plus d'infos, nom, complément d'info de la valeur. Si la couleur est utilisée par beaucoup, mais pas tous les types de Produits que vous pouvait-il en être nullable colonne dans la table Produit, ou tout simplement le mettre dans ProductAdditionalInfo.
Cette approche n'est pas une technique traditionnelle pour une base de données relationnelle, mais je l'ai vu beaucoup utilisé dans la pratique. Il peut être flexible et avoir de bonnes performances.
Steve Yegge appelle cette les Propriétés du modèle et a écrit un long post sur son utilisation.
3 columns: product ID, additional info name, additional info value
j'ai bien compris le concept. Et j'ai effectivement fait cela avant, et a couru dans des problèmes. Cependant, je ne me souviens pas en ce moment que les problèmes ont été.