|
Publicité ' | ||||||||||||||||||||||||
|
|
#1 |
|
Nouveau Membre du Club
![]() Inscription : septembre 2008 Messages : 115 ![]() |
Bonjour,
Je cherche à concevoir une base de données « recette ». Le procédé peut paraître commun et simple mais un grand souci d’historique se pose. Je m’explique : Ci-dessous un modèle conceptuel de donnée relativement simplifié : ![]() Maintenant je veux pouvoir modifier des données, tels que: -quantité d'un ingrédient -ordre des ingrédients -supprimer un ingrédient - un ingrédient peut intervenir plusieurs fois dans une recette avec un ordre différent. Tout en sauvegardant les anciennes valeurs. C'est à dire que je veux pouvoir retrouver les quantités et les ingrédients que j'ai utilisé dans mes recettes sauvegardés. Donc il ne m'est pas autorisé de modifier (ni supprimer) une ligne de la BDD Une solution fonctionnelle à cela est de créer un nouvelle table contenant des révisions de recette: ![]() Donc je peux modifier une recette, il suffirait de faire une nouvelle révision si besoin est. C'est à dire que si j'ai besoin de modifier une quantité d'un ingrédient, je dois créer un nouvelle révision et indiquer la date à laquelle je l'ai faite. Ainsi avec cette date je pourrais retrouver mes anciennes compositions et je pourrait également affiché que les "nouvelles" recettes. Le souci est que si une recette est constitué de 5000 ingrédients et que je m'aperçois au bout d'une semaine d'utilisation que l'ingrédient x n'est pas nécessaire, je vais devoir créer une nouvelles révision et sauvegarder à nouveau 4999 lignes identiques aux autres Quel gaspillage Mon modèle ne serait donc pas optimisé... Quelqu'un aurait-il une meilleur solution ? |
|
|
20
|
|
|
#2 |
|
Expert Confirmé Sénior
![]() ![]() ![]() Spécialiste en bases de données Inscription : septembre 2006 Messages : 2 882 ![]() |
Bonsoir Vilukariok,
Faut pas pleurer, on devrait arriver à faire quelque chose... Par référence à l’ouvrage de Lorentzos, Date et Darwen Temporal Data and the Relational Model, il faut isoler les données historisées des données en cours (voyez aussi le support de cours de Hugh Darwen). J’utilise la notation E/R pour le MCD, car avec Merise, la prise en compte du temps n’est pas adaptée (nécessité d’une entité-type DATE et d’une entité-type PERIODE quand la date ou la période fait partie de l’identifiant d’une association-type, et là, y a du monde). MCD MLD Observations : Chaque attribut de la table RECETTE fait l'objet d'une table d'historisation (en l'occurrence Quantité et OrdreInsertion). La table RECETTE ne contient que les données actives, et chacune d’elle est datée, afin de pouvoir la comparer avec son homologue en historique. La paire {RecetteId, IngredientId} est datée elle aussi (attribut RecetteDepuis). La table RECETTE_HISTORIQUE sert à historiser les recettes dont on ne garde pas la trace dans la table RECETTE (quitte à faire revivre ces recettes un jour ou l’autre). La table QUANTITE_HISTORIQUE est utilisée seulement pour les quantités historisées. ORDRE_INSERTION_HISTORIQUE est utilisée seulement pour les ordres d’insertions historisés. Les attributs RecetteDurant, QuantiteDurant et OrdreInsertionDurant sont du type INTERVAL_DATE : [di : dj] où di représente une date de début de période et dj la date de fin correspondante. Si votre SGBD ne vous permet pas de mettre en œuvre le type INTERVAL_DATE, vous utiliserez des dates de début et de fin. Si vous utilisez des timestamps plutôt que des dates, le principe est le même, avec utilisation du type INTERVAL_TIMESTAMP, mutatis mutandis. Le but de la manœuvre est de n’historiser que ce qui doit l’être : si à telle date vous historisez une quantité, pourquoi historiser aussi le reste ? (Attention, quand vous historisez la quantité, seule la table QUANTITE_HISTORIQUE est mise à jour, la table RECETTE_HISTORIQUE n’est pas concernée). Cette modélisation peut vous surprendre, mais simplifie grandement les opérations et permet d’être plus parcimonieux quant au stockage. N.B. Quand vous dessinez des carrés et des ronds, merci de les faire moins grands... Bon appétit !
__________________
_ Faites simple, mais pas plus simple ! (A. Einstein) E=mc², mais si on discute un peu, on peut l’avoir pour beaucoup moins cher... (G. Lacroix, « Les Euphorismes de Grégoire ») => La relativité n'existerait donc que relativement aux relativistes (Jean Eisenstaedt, « Einstein et la relativité générale ») __________________ Bases de données relationnelles et normalisation : de la première à la sixième forme normale (Bonne lecture !) |
|
|
00
|
|
|
#3 |
|
Nouveau Membre du Club
![]() Inscription : septembre 2008 Messages : 115 ![]() |
Merci de votre réponse fsmrel.
Et merci égalemment du conseil pour ces livres dont vous parlez. Je vais me renseigner sur ce livre: "Temporal Data and the Relational Model", peut être pourra-t-il m'aider à résoudre bien des soucis d'historique et de pérennité d'informations. Je prend connaissance de votre modèle et je suis en train de le mettre en application pour y voir plus clair. Les questions fuseront dès que j'aurais saisi toutes les subtilités (qui sont encore flou pour moi Déjà le principe de sauvegarder que ce qui doit l’être est très intéressant Mais dans ce cas là une première question me viens à l'esprit: Si je veux généraliser ce modèle et l'utiliser pour d'autre applications plus grande, je devrais utiliser une table d'historisation pour chaque paramètre qui entre dans la table active (table recette dans ce cas présent)? |
|
|
00
|
|
|
#4 | ||
|
Expert Confirmé Sénior
![]() ![]() ![]() Spécialiste en bases de données Inscription : septembre 2006 Messages : 2 882 ![]() |
Bonjour Vilukariok,
Citation:
chez amazon.fr, on ne le lit pas comme un roman et il pourrait dérouter celui qui n’est pas préparé. Par ailleurs, l’essentiel figure au chapitre 23 du célèbre An Introduction to Database Systems de C.J. Date (de l’ordre de près de 800 000 mille exemplaires vendus). En tout cas, si vous avez des problèmes de compréhension, posez vos questions ici. Je ne dis pas que je saurai répondre à toutes, mais bon, « fusez » quand même.Citation:
N.B. Le terme paramètre ne convient pas pour une table, il faut parler d’attribut (ou de colonne dans le cas du Sorry Query Language, alias SQL) Une certaine appréhension pourra peut-être vous saisir à l’idée de multiplier le nombre de tables : certes c’est un certain prix à payer, mais le retour sur investissement est juteux. Pour ma part, j’ai mis en place des bases de données de mille tables et plus sans problème, après urbanisation de tout ce monde-là. En effet, il ne faut pas confondre bases de données et écuries d’Augias. L'art ![]() Bon courage !
__________________
_ Faites simple, mais pas plus simple ! (A. Einstein) E=mc², mais si on discute un peu, on peut l’avoir pour beaucoup moins cher... (G. Lacroix, « Les Euphorismes de Grégoire ») => La relativité n'existerait donc que relativement aux relativistes (Jean Eisenstaedt, « Einstein et la relativité générale ») __________________ Bases de données relationnelles et normalisation : de la première à la sixième forme normale (Bonne lecture !) |
||
|
|
00
|
|
|
#5 | |
|
Nouveau Membre du Club
![]() Inscription : septembre 2008 Messages : 115 ![]() |
Citation:
Ceci dit, allez hop, j'urbanise: Je me suis permis de reprendre votre schéma en modifiant le type "INTERVAL_DATE". En effet mon SGBG ne me le permet pas, je compte donc utiliser une "dateDebut" et une "dateFin". ![]() Maintenant mon cahier des charges me dit que: Un ingrédient peut intervenir plusieurs fois dans un recette à un ordre différent. Deux solutions s'offrent à moi: - Faire une clef primaire unique et autoincrementante dans la table "recette" - Rajouter l'attribut "Ordre" en clef primaire Pour l'instant je ne visualise pas la limite et la différence entre ces 2 options. Peut être même qu'une autre solution serait plus judicieuse? |
|
|
|
00
|
|
|
#6 | |||||||
|
Expert Confirmé Sénior
![]() ![]() ![]() Spécialiste en bases de données Inscription : septembre 2006 Messages : 2 882 ![]() |
Bonsoir Vilukariok,
Commencez par la bible, à savoir An Introduction to Database Systems( 8th edition) Citation:
Si le nom de la recette est « Le poulet à la fsmrel » et que l’on utilise d’abord l’ingrédient crème chantilly puis l’ingrédient mayonnaise, on aura la recette r1 (pour laquelle la quantité est q1) alors que pour la variante r2 de ce même poulet à la fsmrel on utilisera d’abord la mayonnaise avant la crème chantilly (la quantité peut rester q1 ou devenir q2). C’est bien cela ? Citation:
Avant de traiter de l’évolution du modèle, ce dont nous parlerons plus tard, j’ai des remarques à faire concernant ce que nous avons vu jusqu’ici. Je vous en prie, il est fait pour ça... Si donc je me suis planté, je ne serai pas seul à prendre un savon... Citation:
Affaiblissons donc le système et simulons les périodes à coup de paires de dates de début et de fin. Le MCD que je vous propose diffère légèrement du vôtre en ce qui concerne les identifiants. En effet, si l’on prend par exemple le cas de la table RECETTE_HISTORIQUE, vous avez défini une clé primaire : {RecetteId, IngredientId, RecetteDurantDeb, RecetteDurantFin}Laquelle est réductible à : {RecetteId, IngredientId, RecetteDurantDeb}Et pour ne pas faire de jaloux, et pour des raisons de symétrie, on peut définir une clé alternative : {RecetteId, IngredientId, RecetteDurantFin}Pour ces histoires de différents types de clés et de leur réductibilité, il serait peut-être bon que vous relisiez l’article Bases de données relationnelles et normalisation, à partir du paragraphe 3.2.2. Ceci dit, ces clés ayant des dates entrant dans leur composition ne garantissent rien... En effet, si par exemple pour la recette r01 et l’ingrédient 01, l’attribut RecetteDurantDeb de la table RECETTE_HISTORIQUE prend la valeur 2001-01-05 et l’attribut RecetteDurantFin prend la valeur 2001-01-15, nous ne pouvons pas empêcher l’ajout dans cette table d’un tuple du genre : <r01, i01, 2001-01-06, 2001-01-17>C’est une vraie passoire. Premières contraintes élémentaires à prévoir : Il faut s’assurer que la date de fin d’une période donnée n’est pas antérieure à la date de début de cette période. C’est le rôle de la contrainte RECETTE_HISTORIQUE_CHK01 ci-dessous : Code SQL :
Comme on l’a vu (effet passoire), Il faut s’assurer que les dates ne se chevaucheront pas. Un trigger pour les INSERT conviendra : Code SQL :
Et s’il s’avère nécessaire de modifier les dates historisées (ce qui en principe ne devrait pas se produire), il faudra prévoir un trigger de type INSTEAD OF UPDATE, toujours pour se prémunir contre les recouvrements de périodes. Suite au prochain épisode. Et n'abusez pas de la crème chantilly à la mayonnaise...
__________________
_ Faites simple, mais pas plus simple ! (A. Einstein) E=mc², mais si on discute un peu, on peut l’avoir pour beaucoup moins cher... (G. Lacroix, « Les Euphorismes de Grégoire ») => La relativité n'existerait donc que relativement aux relativistes (Jean Eisenstaedt, « Einstein et la relativité générale ») __________________ Bases de données relationnelles et normalisation : de la première à la sixième forme normale (Bonne lecture !) |
|||||||
|
|
00
|
|
|
#7 | ||
|
Nouveau Membre du Club
![]() Inscription : septembre 2008 Messages : 115 ![]() |
Citation:
Je peux même rajouter qu'il est possible que l'on décide que la variante r2 manque de sauce mayonnaise. Donc que la recette r2 soit finalement faite dans cet ordre précisément: mayonnaise / chantilly / œuf / mayonnaise / poivre On peux égalemment s'apercevoir un jour que ce n'est pas très digest.Et donc finalement qu'il faut enlever l'œuf. Ce qui donne: mayonnaise / chantilly / mayonnaise / poivre d'où le besoin d'un attribut supplémentaire dans la clef primaire. Citation:
Ce qui me bloque un peu pour l'application de la fin de votre message. Mais ce qui ne m'empêche pas de comprendre ce qui y est dit. Je suis deja plongé dedans |
||
|
|
00
|
|
|
#8 | ||||||||
|
Expert Confirmé Sénior
![]() ![]() ![]() Spécialiste en bases de données Inscription : septembre 2006 Messages : 2 882 ![]() |
Bonsoir Vilukariok,
Ne serait-ce pas plutôt MySQL 4.1 ? Si oui, il serait préférable de passer à une version postérieure... Par ailleurs, vous pouvez toujours vous exercer avec SQL Server Express (gratuit), comme je le fais moi-même, bien que ce ne soit pas mon SGBD habituel. Exact, et cet attribut serait donc OdreInsertion... Dans cette optique, la table ORDRE_INSERTION_HISTORIQUE est absorbée par la table RECETTE_HISTORIQUE. Comme j’ai des problèmes pour afficher les images, je passe directement en mode SQL. Je rappelle que normalement les attributs participant à une clé primaire sont plutôt du type INTEGER, mais pour tester il m’est plus facile de passer au type CHAR. Tables RECETTE_NOM et INGREDIENT : Code SQL :
Table RECETTE : Code SQL :
Table RECETTE_HISTORIQUE : Code SQL :
Table QUANTITE_HISTORIQUE : Code SQL :
), ces définitions de tables vous conviennent-elles ?
__________________
_ Faites simple, mais pas plus simple ! (A. Einstein) E=mc², mais si on discute un peu, on peut l’avoir pour beaucoup moins cher... (G. Lacroix, « Les Euphorismes de Grégoire ») => La relativité n'existerait donc que relativement aux relativistes (Jean Eisenstaedt, « Einstein et la relativité générale ») __________________ Bases de données relationnelles et normalisation : de la première à la sixième forme normale (Bonne lecture !) |
||||||||
|
|
00
|
|
|
#9 | |||
|
Nouveau Membre du Club
![]() Inscription : septembre 2008 Messages : 115 ![]() |
Bonjour,
Citation:
Vous aviez bien compris: il s'agit de MySQL 4.1 Citation:
Citation:
Mais déjà, merci beaucoup pour votre aide. |
|||
|
|
00
|
|
|
#10 | |
|
Nouveau Membre du Club
![]() Inscription : septembre 2008 Messages : 115 ![]() |
Citation:
Au champ 'char(04)' et 'datetime' près ![]() Petite question-remarque: 1) Les 2 tables d'historisation ne sont remplies que lorsqu'une recette change? En effet, je ne sais pas si il y a une utilité à pré remplir les tables d'historisation en laissant vide les champs "Fin". |
|
|
|
00
|
|
|
#11 | ||
|
Expert Confirmé Sénior
![]() ![]() ![]() Spécialiste en bases de données Inscription : septembre 2006 Messages : 2 882 ![]() |
Bonsoir Vilukariok,
Nous sommes en phase en ce qui concerne le diagramme (MLD). Citation:
1er cas de figure : Supposons qu’une recette (table RECETTE) ait la valeur suivante (pour mon confort personnel, je passe en CHAR(04) RecetteId = 'r01'Et que la quantité passe à 200 à la date du '2000-04-22' : On historise donc et la table QUANTITE_HISTORIQUE va héberger la ligne suivant : RecetteId = 'r01'Tandis qu’en échange, dans la table RECETTE on aura la ligne suivante : RecetteId = 'r01'La recette < 'r01', 'i01', 'o01'> existe toujours, simplement on trace la modification des quantités. Deuxième cas de figure : C’est l’attribut Ordre qui change de valeur. Considérons la recette : RecetteId = 'r01'Et supposons qu’elle soit remplacée le '2000-07-14', par la nouvelle recette 'r01', 'i01', 'o02'>. La recette d’ordre 'o01' peut être conservée telle quelle dans la table RECETTE si on la considère comme étant finalement toujours active, ou bien on peut préférer l’expulser dans la table RECETTE_HISTORIQUE (je rappelle que la table RECETTE exprime ce qui est actif et n’a pas intérêt à être surchargée par des données mortes qui la rendraient obèse). La table RECETTE_HISTORIQUE accueille alors la ligne suivante : RecetteId = 'r01'La trace de la quantité sera évacuée dans la table QUANTITE_HISTORIQUE : RecetteId = 'r01'Tandis que la nouvelle recette viendra remplacer l’ancienne dans la table RECETTE : RecetteId = 'r01'En tout cas, une chose est sûre : tout ce qui part en historisation a forcément une date de fin. Quand je lis ceci : Citation:
Laisser « vides » les dates de fin est contraire au principe même de l’historisation où l’on ne doit raisonner qu’en intervalles (ou périodes si vous préférez). Si vous scrutez attentivement les structures de tables que je vous ai proposées, vous constaterez que chaque attribut est qualifié NOT NULL, sans exception. Pour en revenir au plat de résistance : Avec le trigger que je vous avais proposé, vous aviez pu constater que le recouvrement (ou chevauchement) d’intervalles était interdit. Pour aller plus avant, voici les règles de base de l’historisation quant aux contraintes auxquelles celle-ci doit se plier (elles font partie des nine requirements définis par Date, Darwen et Lorentzos) : 1) Si la base de données montre qu’il y a une recette r au jour j, elle ne doit contenir qu’un seul tuple qui exprime ce fait.Il existe d’autres contraintes, mais celles que j’ai énumérées sont incontournables. Par ailleurs, vous pourriez préférer que la table RECETTE_HISTORIQUE soit absorbée par la table QUANTITE_HISTORIQUE, pour cause de double emploi apparent. Mais attention, les intervalles [RecetteDurantDeb:RecetteDurantDeb] et [QuantiteDurantDeb:QuantiteDurantDeb] vivent a priori chacun sa vie. Par ailleurs, que faire le jour où, en plus de l’attribut Quantite, vous définiriez un attribut supplémentaire pour les recettes (la qualité recherchée, l’inventeur de la chose ou que sais-je) ? Vous seriez coincé et obligé de bien réfléchir à toutes les conséquences sur les applications déjà développées d'un retour à l'architecture que je vous ai proposée. La table RECETTE_HISTORIQUE est une sorte de tour de contrôle pour l'historisation.En tout cas, les six contraintes qui précèdent font l’objet de triggers intéressants (je vous laisse réfléchir un peu au pseudo-code correspondant), il y a un prix à payer pour que la base de données ne finisse pas par ressembler à n’importe quoi (quand on voit ce qu'on voit...) A suivre...
__________________
_ Faites simple, mais pas plus simple ! (A. Einstein) E=mc², mais si on discute un peu, on peut l’avoir pour beaucoup moins cher... (G. Lacroix, « Les Euphorismes de Grégoire ») => La relativité n'existerait donc que relativement aux relativistes (Jean Eisenstaedt, « Einstein et la relativité générale ») __________________ Bases de données relationnelles et normalisation : de la première à la sixième forme normale (Bonne lecture !) |
||
|
|
00
|
|
|
#12 | |
|
Nouveau Membre du Club
![]() Inscription : septembre 2008 Messages : 115 ![]() |
Bonjour fsmrel,
Tout d'abord, merci encore pour toutes ces informations, en plus de me guider et me conseiller la bonne façon pour résoudre mon problème, j'apprends une quantité d'information non négligeable. Merci! Ensuite, je me permet de revenir sur un de vos propos: Citation:
QuantiteDurantFin = '2000-04-21' ? et RecetteDepuis = '2000-01-15' ? Sinon je suis un peu perdu... Ensuite pour le deuxième cas de figure, je suis entièrement d'accord avec vous. Cependant si je me projette dans l'avenir, je vois que récupérer les données correspondants à une date antérieur ne vas pas être un exercice simple. Prenons comme exemple toujours votre deuxième cas de figure: La fameuse recette que vous voulez changer contient 50 ingrédients. Je pars du principe que le changement de l'ordre a été effectué (tel que vous l'avez fait). Votre changement correspondait par exemple à déplacer un constituant pour le mettre en dernière position dans la recette. Je dois maintenant retrouver la recette qui à été utilisé le '2000-06-01'. Diantre.. Ces informations sont dispatchées dans ces 3 tables... Il va donc falloir que je fasse une requête sur l'ensemble de mes tables: RECETTE , RECETTE_HISTORIQUE et QUANTITE_HISTORIQUE. Cette requête va peut-être être du type JOIN ou UNION ou les 2? Ou alors il est peut être plus judicieux de déplacer entièrement la recette dans les 2 tables d'historisation lors d'un tel changement? Et enfin: Je suis tout à fait d'accord avec ces 'nine requirements' .Cela montre bien le fonctionnement de cette future BDD. Je pense que cet exemple de BDD 'recette' va m'être très utile pour toutes mes futures applications. Merci. Merci |
|
|
|
00
|
|
|
#13 | |
|
Expert Confirmé Sénior
![]() ![]() ![]() Spécialiste en bases de données Inscription : septembre 2006 Messages : 2 882 ![]() |
Bonjour Vilukariok,
Citation:
)Il est évident que l’attribut RecetteDepuis de la table RECETTE n’est pas concerné par la modification de la quantité et que sa valeur reste égale à '2000-01-15'. De même, l’attribut QuantiteDurantFin de la table QUANTITE_HISTORIQUE prend bien entendu la valeur '2000-04-21'. En tout cas, on voit que vous suivez Voilà pour un premier temps. Je vais maintenant regarder la suite de votre message.
__________________
_ Faites simple, mais pas plus simple ! (A. Einstein) E=mc², mais si on discute un peu, on peut l’avoir pour beaucoup moins cher... (G. Lacroix, « Les Euphorismes de Grégoire ») => La relativité n'existerait donc que relativement aux relativistes (Jean Eisenstaedt, « Einstein et la relativité générale ») __________________ Bases de données relationnelles et normalisation : de la première à la sixième forme normale (Bonne lecture !) |
|
|
|
00
|
|
|
#14 | |||
|
Nouveau Membre du Club
![]() Inscription : septembre 2008 Messages : 115 ![]() |
Citation:
Lors de mon dernier message, j'ai aborder le faite de retrouver une recette utilisé à une date antérieur: Je pense qu'il me faudra donc utiliser une requete de ce type: Code :
Donc à priori c'est normal? |
|||
|
|
00
|
|
|
#15 | ||||||||||
|
Expert Confirmé Sénior
![]() ![]() ![]() Spécialiste en bases de données Inscription : septembre 2006 Messages : 2 882 ![]() |
Bonjour Vilukariok,
Citation:
L’opérateur UNION est évidemment bien mis à contribution (les ensembles étant ici disjoints, sa version UNION ALL est ici intéressante pour éviter des tris inutiles). Si vous cherchez seulement la (les) recette(s) sur le seul critère de la date à partir de laquelle la recette à cours, et si la quantité ne vous intéresse pas, la requête ci-dessous suffit (ne vous préoccupez pas de l’opérateur CONVERT qui permet en SQL Server la conversion de type, à l’instar de CAST) : Code sql :
Code sql :
Code sql :
Ou encore d'autres variations sur le thème... Citation:
P.-S. J'espère ne pas avoir commis de coquilles avec les copier/coller...
__________________
_ Faites simple, mais pas plus simple ! (A. Einstein) E=mc², mais si on discute un peu, on peut l’avoir pour beaucoup moins cher... (G. Lacroix, « Les Euphorismes de Grégoire ») => La relativité n'existerait donc que relativement aux relativistes (Jean Eisenstaedt, « Einstein et la relativité générale ») __________________ Bases de données relationnelles et normalisation : de la première à la sixième forme normale (Bonne lecture !) |
||||||||||
|
|
00
|
|
|
#16 | ||||
|
Nouveau Membre du Club
![]() Inscription : septembre 2008 Messages : 115 ![]() |
Je suis entièrement d'accord avec vos requêtes, je suis arrivé aux mêmes conclusions que vous, cela me réconforte dans mon projet
Citation:
Citation:
Code :
Du coup je ne sais que penser... |
||||
|
|
00
|
|
|
#17 |
|
Nouveau Membre du Club
![]() Inscription : septembre 2008 Messages : 115 ![]() |
Merci encore fsmrel pour tous ces conseils.
J'ai juste une petite remarque: Si j'ai une recette de 500 ingrédients. Que je m'aperçois qu'il faut placer un nouvel ingrédient en position 200. Je doit donc modifier 300 lignes (uplets). Il faut commencer par sauvegarder dans "recette_historique" et "quantite_historique" ces 300 lignes. Puis rajouter la nouvelle ligne qui correspond au nouvel ingrédient dans "preparation" Et enfin modifier les 300 lignes (décaler OrdreInsertion de +1) de "recette" Cela fait beaucoup de données. Aurais-je intérêt à concevoir d'une manière différente l'ordre? |
|
|
00
|
|
|
#18 | |||||||||||||
|
Expert Confirmé Sénior
![]() ![]() ![]() Spécialiste en bases de données Inscription : septembre 2006 Messages : 2 882 ![]() |
Bonsoir Vilukariok,
Citation:
Oui, car il est hors de question de modifier des tombereaux de lignes ! Pour la table RECETTE, vous avez défini un attribut OrdreInsertion explicite. Pour être minimaliste dans les mises à jour, à savoir insérer une recette entre deux recettes, vous pourriez vous orienter vers la mise en œuvre d’une chaîne. Cette chaîne ferait l’objet d’une table, appelons-la MAILLON. Dans le diagramme ci-dessous, l’attribut OrdreInsertion disparaît, au bénéfice de la nouvelle table. La structure de la table RECETTE changerait du fait de la disparition de l’attribut OrdreInsertion et de l'ajout d'un attribut, appelons-le RecetteSeq, ayant pour objet lui aussi de permettre d’avoir des variantes pour la paire {RecetteId, IngredientId}, mais sans qu’il joue de rôle fonctionnel : peu importe les valeurs dont on l’affecte. Maintenant, si OrdreInsertion ne joue pas vraiment de rôle fonctionnel, on le conserve et RecetteSeq n'a pas lieu d'être. Pour ne pas surcharger, je ne fais pas figurer ici les tables dévolues à l’historisation (qui évoluent, dans la mesure où l’attribut OrdreInsertion y est à remplacer par l’attribut RecetteSeq). En SQL : Code SQL :
Code SQL :
Code SQL :
Créons des recettes pour la paire <'r01', 'i01'> : Code SQL :
Le maillon '002' a pour prédécesseur '001' qui lui-même n’est précédé par personne. Le maillon '003' a pour prédécesseur '002', etc. : Code SQL :
Créons une variante '151' de la recette <'r01', 'i01'>, qui se glissera le moment voulu entre '002' et '003' : Code SQL :
INSERT INTO RECETTE VALUES ('r01', 'i01', '151', '2001-01-25', '2001-01-25', 150) ; Faisons précéder '003' par '151' : Code SQL :
Et faisons glisser '151' entre 002' et '003' : Code SQL :
INSERT INTO MAILLON VALUES ('r01', 'i01', '151', '002') ; Cette méthode n’est pas gourmande en mise à jour, mais reste à savoir si elle vous convient, l’attribut OrdreInsertion passant le cas échéant à la trappe, ce qui serait gênant s’il a vraiment un rôle fonctionnel. A vous de voir et d’adapter.
__________________
_ Faites simple, mais pas plus simple ! (A. Einstein) E=mc², mais si on discute un peu, on peut l’avoir pour beaucoup moins cher... (G. Lacroix, « Les Euphorismes de Grégoire ») => La relativité n'existerait donc que relativement aux relativistes (Jean Eisenstaedt, « Einstein et la relativité générale ») __________________ Bases de données relationnelles et normalisation : de la première à la sixième forme normale (Bonne lecture !) |
|||||||||||||
|
|
00
|
|
|
#19 |
|
Nouveau Membre du Club
![]() Inscription : septembre 2008 Messages : 115 ![]() |
Whaou
extraordinaire!J'essayai justement de trouver un système similaire. Je prend note, je relie et j'essaie de suite dans mon SGBD. Mille merci. Je vous tiens au courant |
|
|
00
|
|
|
#20 | ||||||
|
Nouveau Membre du Club
![]() Inscription : septembre 2008 Messages : 115 ![]() |
J'aurais juste une petite remarque:
Code :
Code :
Code :
Donc il ne faudrait pas faire cette déclaration de "MAILLON_RECETTE_FK2"? Ensuite: Je suis en train de faire une requêtes pour sélectionner la recette dans le bon ordre. Je m'aperçois que ce n'est pas un exercice facile. Pour l'instant je n'ai pas encore réussi. J'ai bien trouvé un système mais j'utilise beaucoup trop de requêtes pour y parvenir. Je m'y penche et vous transmet mes idées. Merci |
||||||
|
|
00
|
Copyright © 2000-2012 - www.developpez.com