tag:forum.selfhtml.org,2005:/self unterschiedliche logisch Beziehungen in einer DB-Tabelle speichern – SELFHTML-Forum 2019-10-21T09:44:45Z https://forum.selfhtml.org/self/2019/oct/19/unterschiedliche-logisch-beziehungen-in-einer-db-tabelle-speichern/1759020#m1759020 wKovacs 2019-10-19T12:02:17Z 2019-10-19T12:03:18Z unterschiedliche logisch Beziehungen in einer DB-Tabelle speichern <p>Hallo,</p> <p>ich habe gerade wohl einen Konten im Kopf und hoffe jemand kann mich in die richtige Richtung weisen.</p> <p>Mein Problem:</p> <p>Ich habe eine Liste von Weiterbildungskursen (nennen wir sie KursA bis KursZ) in einer Tabelle abgelegt. Einige diese Kurse haben Vorraussetzungen aus einer Kombination von anderen Kursen.</p> <p>Beispiel: KursA ODER (KursB UND KursC)</p> <p>Diese Beziehungen können pro Kurs unterschiedlich sein, nicht nur unterschiedliche Anzahl an Alternativen (ODER) sondern auch Kombinationen (UND).</p> <p>Ich versuche einen Weg zu finden, diese Beziehungen in einer Tabelle abzubilden.</p> <p>etwa:</p> <p>dabei ist "fürKurs" ein Fremdschlüssel der entweder auf die Kurstabelle verweist oder auf sich selbst.</p> <table> <thead> <tr> <th>fürKurs</th> <th>Bed1</th> <th>verknüpfung</th> <th>bed2</th> </tr> </thead> <tbody> <tr> <td>KursK</td> <td>KursA</td> <td>oder</td> <td>2</td> </tr> <tr> <td>2</td> <td>KursB</td> <td>und</td> <td>KursC</td> </tr> </tbody> </table> <p>Nun habe ich 2 Probleme die ich aktuell sehe:</p> <p>A wie unterscheide ich, auf welche Tabelle sich der Fremdschlüssel bezieht, mal ganz davon abgesehen, wie kann ich eine Spalte auf 2 Tabellen referenzieren lassen</p> <p>B Mit diesem Entwurf kann ich sowas wie KursA UND (KursB ODER (KursC UND KursD) ODER KursE) nicht abbilden.</p> <p>Ich gehe davon aus, das schon der Ansatz falsch ist. </p> <p>Dagegen vermute (hoffe) ich, dass es ähnliche Probleme häufiger gibt und es eine Lösung gibt. Bisher war ich nur noch nicht in der Lage sie zu finden. Falls jemand einen Lösungsansatz hat oder auch nur einen Link zu relevanten Lesestoff (auch englisch) wäre ich sehr dankbar!</p> <p>Vielen Dank</p> <p>wKovacs</p> https://forum.selfhtml.org/self/2019/oct/19/unterschiedliche-logisch-beziehungen-in-einer-db-tabelle-speichern/1759021#m1759021 Email https://rolfrost.de/dbiutf8.html 2019-10-19T14:17:14Z 2019-10-19T14:17:14Z unterschiedliche logisch Beziehungen in einer DB-Tabelle speichern <p>Interessante Aufgabe. Ich würde die Lösung mit Bitoperatoren für UND//OR angehen. Hierfür muss für jeden Kurstype ein numerischer Basiswert aus dem Dualsystem überlegt werden und zwar so daß die Verknüpfung einen eindeutigen Wert ergibt aus dem die darin enthaltenen Kurstypen erkenntlich sind.</p> <p>MFG</p> https://forum.selfhtml.org/self/2019/oct/19/unterschiedliche-logisch-beziehungen-in-einer-db-tabelle-speichern/1759023#m1759023 Camping_RIDER janosch.zoller@selfhtml.org http://www.campingrider.de 2019-10-19T16:29:23Z 2019-10-19T16:35:14Z unterschiedliche logisch Beziehungen in einer DB-Tabelle speichern <p>Aloha ;)</p> <p>Zunächst: wenn du das vorstehende <a href="https://forum.selfhtml.org/self/2019/oct/19/unterschiedliche-logisch-beziehungen-in-einer-db-tabelle-speichern/1759021#m1759021" rel="noopener noreferrer">Geschwurbel</a> nicht verstanden hast, denk dir nichts dabei. Manch Lösung eines genialen Geistes ist für solche wie uns einfach unverständlich.</p> <blockquote> <p>etwa:</p> <p>dabei ist "fürKurs" ein Fremdschlüssel der entweder auf die Kurstabelle verweist oder auf sich selbst.</p> <table> <thead> <tr> <th>fürKurs</th> <th>Bed1</th> <th>verknüpfung</th> <th>bed2</th> </tr> </thead> <tbody> <tr> <td>KursK</td> <td>KursA</td> <td>oder</td> <td>2</td> </tr> <tr> <td>2</td> <td>KursB</td> <td>und</td> <td>KursC</td> </tr> </tbody> </table> <p>Nun habe ich 2 Probleme die ich aktuell sehe:</p> <p>A wie unterscheide ich, auf welche Tabelle sich der Fremdschlüssel bezieht, mal ganz davon abgesehen, wie kann ich eine Spalte auf 2 Tabellen referenzieren lassen</p> </blockquote> <p>"Einfach" geht das nicht. Ich schlage daher einen leicht geänderten Ansatz vor:</p> <table> <thead> <tr> <th>ID</th> <th>fürKurs</th> <th>Element</th> <th>verknüpfung</th> <th>mit</th> </tr> </thead> <tbody> <tr> <td>0</td> <td>KursK</td> <td>KursA</td> <td>oder</td> <td>1</td> </tr> <tr> <td>1</td> <td>KursK</td> <td>KursB</td> <td>und</td> <td>2</td> </tr> <tr> <td>2</td> <td>KursK</td> <td>KursC</td> <td>oder</td> <td>Null</td> </tr> </tbody> </table> <p>So ist an jeder Spalte klar, für welche Tabelle der Schlüssel gilt.</p> <p>Hinweis: Ich ging jetzt mal davon aus, dass du die Angabe fürKurs an der Stelle zwingend brauchst. Es wäre im vorliegenden Datenmodell aber auch möglich, diese Spalte an der Stelle komplett rauszulassen und in einer weiteren Tabelle (zwei Spalten: fürKurs und startID) den Kurs mit dem ersten Bedingungsteil zu verknüpfen. Das hat Vorteile, unter anderem ist es Speicherplatz-effizienter und du kannst zusätzlich Eindeutigkeit bei fürKurs fordern.</p> <blockquote> <p>B Mit diesem Entwurf kann ich sowas wie KursA UND (KursB ODER (KursC UND KursD) ODER KursE) nicht abbilden.</p> </blockquote> <p>Doch, kannst du! Du musst die Bedingung nur gleichwertig umordnen:</p> <p>KursA UND (KursB ODER (KursE ODER (KursC UND KursE)))</p> <p>In deinem Beispiel war ein oder-oder drin. Das lässt sich in zwei hintereinander ausgeführte oders umschreiben. Das klappt für alle und- bzw. oder-Verknüpfungen, weil diese assoziativ und kommutativ sind.</p> <p>Wie du die Eingabemöglichkeit gestaltest steht auf einem anderen Blatt, aber entweder muss deine Software vor dem Speichern umordnen oder (wahrscheinlicher) es stellt sich heraus, dass es für dich schon bei der Eingabe geschickt ist, ein solches Format zu fordern.</p> <p>Ich hoffe die Idee hilft dir weiter.</p> <p>Grüße,</p> <p>RIDER</p> <div class="signature">-- <br> Camping_RIDER a.k.a. Riders Flame a.k.a. Janosch Zoller<br> # <a href="https://twitter.com/Camping_RIDER" rel="nofollow noopener noreferrer">Twitter</a> # <a href="http://steamcommunity.com/id/Camping_RIDER" rel="nofollow noopener noreferrer">Steam</a> # <a href="https://www.youtube.com/user/RidersFlame" rel="nofollow noopener noreferrer">YouTube</a> # <a href="http://wiki.selfhtml.org/wiki/Benutzer:Camping_RIDER" rel="nofollow noopener noreferrer">Self-Wiki</a> # <a href="http://community.de.selfhtml.org/fanprojekte/selfcode.htm" rel="nofollow noopener noreferrer">Selfcode</a>: sh:) fo:) ch:| rl:) br:^ n4:? ie:% mo:| va:) js:) de:> zu:} fl:( ss:) ls:[ </div> https://forum.selfhtml.org/self/2019/oct/19/unterschiedliche-logisch-beziehungen-in-einer-db-tabelle-speichern/1759025#m1759025 Email https://rolfrost.de/dbiutf8.html 2019-10-19T18:05:31Z 2019-10-19T18:07:28Z unterschiedliche logisch Beziehungen in einer DB-Tabelle speichern <blockquote> <p>Interessante Aufgabe. Ich würde die Lösung mit Bitoperatoren für UND//OR angehen. Hierfür muss für jeden Kurstype ein numerischer Basiswert aus dem Dualsystem überlegt werden und zwar so daß die Verknüpfung einen eindeutigen Wert ergibt aus dem die darin enthaltenen Kurstypen erkenntlich sind.</p> </blockquote> <p>Ansatz mit 4 Kursen:</p> <pre><code class="block language-text">1 1 1 1 | | | |_ Kurs A | | | | | |_Kurs B | | | |_ Kurs C | |_ Kurs D Magister = 2^0 + 2^1 + 2^2 + 2^3 (alle Kurse) Bachelor = A + B oder A + C Beginner = A HI = D oder C usw. </code></pre> <p>So ergeben sich numerische Werte die eindeutig beschreiben welche Kurse belegt sein müssen für einen bestimmten Abschluss. Wobei diese Werte logisch veknüpft werden können.</p> <p>Anders ausgedruückt: Gibt den Kursen numerische Wertigkeiten dann kannst Du damit rechnen.</p> <p>Denke an die Skalierbarkeit!</p> <p>Also ich finde die Idee richtig gut.</p> https://forum.selfhtml.org/self/2019/oct/19/unterschiedliche-logisch-beziehungen-in-einer-db-tabelle-speichern/1759024#m1759024 Rolf B 2019-10-19T18:02:42Z 2019-10-19T18:07:23Z unterschiedliche logisch Beziehungen in einer DB-Tabelle speichern <p>Hallo Camping_RIDER,</p> <blockquote> <p>KursA UND (KursB ODER (KursE ODER (KursC UND KursE)))</p> </blockquote> <p>Whoa - wie soll man denn das relational abbilden?</p> <p>Ich habe heute nachmittag angefangen mir Gedanken zu machen und auf meinem lokalen MySQL etwas experimentiert. Das dauerte natürlich eine Weile.</p> <p>Grundsätzlich sollte man, wenn man logische Ausdrücke automatisiert verarbeiten will, eine Normalform dieser Ausdrücke anstreben. Davon gibt's zwei, nämlich die disjunktive und die konjunktive Normalform (Details siehe z.B. Wikipedia). Für mich persönlich ist die diskunktive Form leichter verständlich, darum gehe ich darauf jetzt näher ein.</p> <p>Disjunktive Normalform (DNF) bedeutet, dass man einige Terme hat, die Variablen durch UND verknüpfen (Konjunktion), und diese Terme durch ein ODER (Disjunktion) verknüpft. Außerdem ist es erlaubt, Variablen vor der UND-Verknüpfung zu negieren. Auf diese Weise kann man sozusagen alle Zeilen der Wahrheitstabelle, wo im Ergebnis ein TRUE steht, mehr oder weniger gedankenfrei als UND-Terme aufschreiben und diese Terme ODER verknüpfen.</p> <p>Was fängt man nun damit an? Nehmen wir an, wir hätten folgende Kurse:</p> <p>KursA - HTML Grundlagen<br> KursB - CSS Grundlagen<br> KursC - Großer Webentwickler-Basiskurs<br> KursD - Aufbaukurs GRID</p> <p>Für's Beispiel soll es so sein, dass man für KursD entweder KursA und KursB gemacht haben muss, oder KursC (der beinhaltet KursA und KursB).</p> <p>Das kann man so in eine Tabelle <code>UndTerme</code> bringen:</p> <pre><code class="block">Gruppe VorKurs Erforderlich 101 KursA 1 101 KursB 1 102 KursC 1 103 KursC 0 104 KursC 0 </code></pre> <p>Die Spalte <code>Erforderlich</code> soll angeben, ob dieser Vorkurs vorausgesetzt wird, oder ob dieser Vorkurs zu einer Nichtbelegbarkeit führen soll. Damit wird die Negierungsmöglichkeit einer Variablen abgebildet, die in der DNF vorgesehen ist. Die Gruppe 103 besagt: Wer KursC schon belegt hat, soll etwas nicht tun können.</p> <p>Die Zuordnung von Kurse zu UndTerme erfolgt mit einer Tabelle <code>OderTerme</code>, die angibt, welche Und-Gruppen für einen Kurs mit ODER verknüpft werden müssen:</p> <pre><code class="block">Kurs Gruppe KursD 101 KursD 102 KursA 103 KursB 104 </code></pre> <p>Wer KursD machen will, muss also Gruppe 101 oder Gruppe 102 erfüllen.</p> <p>Wer KursA oder KursB machen will, muss Gruppe 103 bzw. 104 erfüllen. Die erfüllt man aber nur, wenn man KursC <strong>nicht</strong> gemacht hat. Konkret: Wer den Webentwickler-Basiskurs gemacht hat, kann HTML- oder CSS-Grundlagen nicht belegen. Das wäre für denjenigen nämlich nichts Neues mehr.</p> <pre><code class="block language-sql"><span class="token keyword">SELECT</span> Gruppe<span class="token punctuation">,</span> Vorkurs<span class="token punctuation">,</span> Erforderlich <span class="token keyword">FROM</span> OderTerme ot <span class="token keyword">JOIN</span> UndTerme ut <span class="token keyword">ON</span> ot<span class="token punctuation">.</span>gruppe <span class="token operator">=</span> ut<span class="token punctuation">.</span>gruppe <span class="token keyword">WHERE</span> ot<span class="token punctuation">.</span>Kurs <span class="token operator">=</span> <span class="token string">'KursD'</span> </code></pre> <p>liefert dann</p> <pre><code class="block">Gruppe Vorkurs Erforderlich 101 KursA 1 101 KursB 1 102 KursC 1 </code></pre> <p>Das kann man nun Gruppe für Gruppe programmatisch auswerten, um für einen Kunden die Belegbarkeit zu prüfen. Oder Gruppe für Gruppe ausgeben, um dem Kunden die Kursvoraussetzungen anzuzeigen.</p> <p>Oder mit SQL auswerten! Nehmen wir noch eine Tabelle hinzu, <code>KursErfolg</code>, in der für einen Kunden steht, welche Kurse er gemacht und bestanden hat (da würde natürlich im Reallife nicht "Rolf" stehen, sondern eine ID).</p> <pre><code class="block">Kunde Kurs Bestanden Rolf KursA 1 Rolf KursB 0 </code></pre> <p>Diese Tabelle kann ich in das SQL einbeziehen:</p> <pre><code class="block language-sql"><span class="token keyword">SELECT</span> Gruppe<span class="token punctuation">,</span> Vorkurs<span class="token punctuation">,</span> Erforderlich<span class="token punctuation">,</span> Bestanden <span class="token keyword">FROM</span> OderTerme ot <span class="token keyword">JOIN</span> UndTerme ut <span class="token keyword">ON</span> ot<span class="token punctuation">.</span>gruppe <span class="token operator">=</span> ut<span class="token punctuation">.</span>gruppe <span class="token keyword">LEFT</span> <span class="token keyword">JOIN</span> KursErfolg ke <span class="token keyword">ON</span> ke<span class="token punctuation">.</span>Kurs <span class="token operator">=</span> ku<span class="token punctuation">.</span>VorKurs <span class="token operator">AND</span> ke<span class="token punctuation">.</span>Kunde <span class="token operator">=</span> <span class="token string">'Rolf'</span> <span class="token keyword">WHERE</span> ot<span class="token punctuation">.</span>Kurs <span class="token operator">=</span> <span class="token string">'KursD'</span> </code></pre> <p>Ergebnis:</p> <pre><code class="block">Gruppe Vorkurs Erforderlich Bestanden 101 KursA 1 1 101 KursB 1 0 102 KursC 1 NULL </code></pre> <p>Die NULL in Zeile 3 erschwert die weitere Verarbeitung, darum ersetzen wir im SQL noch <code>Bestanden</code> durch <code>COALESCE(Bestanden,0)</code>. Das schreibe ich jetzt nicht auf, jedenfalls wird dadurch ein nicht belegter Kurs wie Nichtbestanden behandelt. Und wir müssen Erforderlich mit Bestanden vergleichen, nur wenn es übereinstimmt, ist dieser Teil der UND-Bedingung erfüllt.</p> <pre><code class="block language-sql"><span class="token keyword">SELECT</span> Gruppe<span class="token punctuation">,</span> Vorkurs<span class="token punctuation">,</span> Erforderlich<span class="token operator">=</span><span class="token keyword">COALESCE</span><span class="token punctuation">(</span>Bestanden<span class="token punctuation">,</span><span class="token number">0</span><span class="token punctuation">)</span> <span class="token keyword">as</span> Zutreffend <span class="token keyword">FROM</span> OderTerme ot <span class="token keyword">JOIN</span> UndTerme ut <span class="token keyword">ON</span> ot<span class="token punctuation">.</span>gruppe <span class="token operator">=</span> ut<span class="token punctuation">.</span>gruppe <span class="token keyword">LEFT</span> <span class="token keyword">JOIN</span> KursErfolg ke <span class="token keyword">ON</span> ke<span class="token punctuation">.</span>Kurs <span class="token operator">=</span> ku<span class="token punctuation">.</span>VorKurs <span class="token operator">AND</span> ke<span class="token punctuation">.</span>Kunde <span class="token operator">=</span> <span class="token string">'Rolf'</span> <span class="token keyword">WHERE</span> ot<span class="token punctuation">.</span>Kurs <span class="token operator">=</span> <span class="token string">'KursD'</span> </code></pre> <p>ergibt</p> <pre><code class="block">Gruppe Vorkurs Zutreffend 101 KursA 1 101 KursB 0 102 KursC 0 </code></pre> <p>Diese Treffermenge können wir nun gruppieren und aggregieren, um pro Und-Term nur noch eine Zeile zu bekommen. Ein UND ist falsch, sobald ein Teil davon falsch ist, wir müssen also MIN(Zutreffend) bilden. Das ist nur 1, wenn alle Teile des UND die 1 tragen. Den Vorkurs können wir jetzt nicht mehr ausgeben, der ist ja nicht gruppiert.</p> <pre><code class="block">SELECT Gruppe, MIN(Erforderlich=COALESCE(Bestanden,0)) as Zutreffend FROM OderTerme ot JOIN UndTerme ut ON ot.gruppe = ut.gruppe LEFT JOIN KursErfolg ke ON ke.Kurs = ku.VorKurs AND ke.Kunde = 'Rolf' WHERE ot.Kurs = 'KursD' GROUP BY Gruppe </code></pre> <p>ergibt</p> <pre><code class="block">Gruppe Zutreffend 101 0 102 0 </code></pre> <p>Das müssen wir nun noch verODERn. Ein ODER ist wahr, sobald ein Teilterm wahr ist. Das bekommen wir mit MAX(Zutreffend) geliefert.</p> <pre><code class="block language-sql"><span class="token keyword">SELECT</span> <span class="token function">MAX</span><span class="token punctuation">(</span>og<span class="token punctuation">.</span>Zutreffend<span class="token punctuation">)</span> <span class="token keyword">FROM</span> <span class="token punctuation">(</span><span class="token keyword">SELECT</span> Gruppe<span class="token punctuation">,</span> <span class="token function">MIN</span><span class="token punctuation">(</span>Erforderlich<span class="token operator">=</span><span class="token keyword">COALESCE</span><span class="token punctuation">(</span>Bestanden<span class="token punctuation">,</span><span class="token number">0</span><span class="token punctuation">)</span><span class="token punctuation">)</span> <span class="token keyword">as</span> Zutreffend <span class="token keyword">FROM</span> OderTerme ot <span class="token keyword">JOIN</span> UndTerme ut <span class="token keyword">ON</span> ot<span class="token punctuation">.</span>gruppe <span class="token operator">=</span> ut<span class="token punctuation">.</span>gruppe <span class="token keyword">LEFT</span> <span class="token keyword">JOIN</span> KursErfolg ke <span class="token keyword">ON</span> ke<span class="token punctuation">.</span>Kurs <span class="token operator">=</span> ku<span class="token punctuation">.</span>VorKurs <span class="token operator">AND</span> ke<span class="token punctuation">.</span>Kunde <span class="token operator">=</span> <span class="token string">'Rolf'</span> <span class="token keyword">WHERE</span> ot<span class="token punctuation">.</span>Kurs <span class="token operator">=</span> <span class="token string">'KursD'</span> <span class="token keyword">GROUP</span> <span class="token keyword">BY</span> Gruppe<span class="token punctuation">)</span> og </code></pre> <p>Das ergibt die 0 als Ergebnis. Falls Rolf KursB bestanden hätte, wäre für Gruppe 101 der Zutreffend-Wert 1 ermittelt worden, und das große SQL liefert dann 1.</p> <p>Ich hoffe, ich habe beim Übertragen von meinem Spiel-MySQL ins Forum keine SQL-Fehler eingebaut. Vollziehe es mal nach, probiere auch mal aus, was passiert, wenn ein Kunde den KursC belegt hat und Du die Voraussetzungen für KursA prüfst.</p> <p>Wie Du das mit einem Editor pflegst, ist natürlich noch eine ganz andere Sache...</p> <p><em>Rolf</em></p> <div class="signature">-- <br> sumpsi - posui - clusi </div> https://forum.selfhtml.org/self/2019/oct/19/unterschiedliche-logisch-beziehungen-in-einer-db-tabelle-speichern/1759028#m1759028 Camping_RIDER janosch.zoller@selfhtml.org http://www.campingrider.de 2019-10-19T20:46:35Z 2019-10-19T20:46:35Z unterschiedliche logisch Beziehungen in einer DB-Tabelle speichern <p>Aloha ;)</p> <blockquote> <blockquote> <p>KursA UND (KursB ODER (KursE ODER (KursC UND KursE)))</p> </blockquote> <p>Whoa - wie soll man denn das relational abbilden?</p> </blockquote> <p>Na, so wie ich schrieb. Ob das optimal ist kann ich nicht beurteilen. Aber möglich ist das so.</p> <p>Grüße,</p> <p>RIDER</p> <div class="signature">-- <br> Camping_RIDER a.k.a. Riders Flame a.k.a. Janosch Zoller<br> # <a href="https://twitter.com/Camping_RIDER" rel="nofollow noopener noreferrer">Twitter</a> # <a href="http://steamcommunity.com/id/Camping_RIDER" rel="nofollow noopener noreferrer">Steam</a> # <a href="https://www.youtube.com/user/RidersFlame" rel="nofollow noopener noreferrer">YouTube</a> # <a href="http://wiki.selfhtml.org/wiki/Benutzer:Camping_RIDER" rel="nofollow noopener noreferrer">Self-Wiki</a> # <a href="http://community.de.selfhtml.org/fanprojekte/selfcode.htm" rel="nofollow noopener noreferrer">Selfcode</a>: sh:) fo:) ch:| rl:) br:^ n4:? ie:% mo:| va:) js:) de:> zu:} fl:( ss:) ls:[ </div> https://forum.selfhtml.org/self/2019/oct/19/unterschiedliche-logisch-beziehungen-in-einer-db-tabelle-speichern/1759029#m1759029 Camping_RIDER janosch.zoller@selfhtml.org http://www.campingrider.de 2019-10-19T20:50:26Z 2019-10-19T20:50:26Z unterschiedliche logisch Beziehungen in einer DB-Tabelle speichern <p>Aloha ;)</p> <blockquote> <p>Also ich finde die Idee richtig gut.</p> </blockquote> <p>Fast genauso gut wie eine relationale Datenbank mit geclusterten Daten zu füttern. Weil sich das so gut mit Parameter-Kontrollstrukturen auswerten lässt. Aber wirklich nur fast so gut.</p> <p>Grüße,</p> <p>RIDER</p> <div class="signature">-- <br> Camping_RIDER a.k.a. Riders Flame a.k.a. Janosch Zoller<br> # <a href="https://twitter.com/Camping_RIDER" rel="nofollow noopener noreferrer">Twitter</a> # <a href="http://steamcommunity.com/id/Camping_RIDER" rel="nofollow noopener noreferrer">Steam</a> # <a href="https://www.youtube.com/user/RidersFlame" rel="nofollow noopener noreferrer">YouTube</a> # <a href="http://wiki.selfhtml.org/wiki/Benutzer:Camping_RIDER" rel="nofollow noopener noreferrer">Self-Wiki</a> # <a href="http://community.de.selfhtml.org/fanprojekte/selfcode.htm" rel="nofollow noopener noreferrer">Selfcode</a>: sh:) fo:) ch:| rl:) br:^ n4:? ie:% mo:| va:) js:) de:> zu:} fl:( ss:) ls:[ </div> https://forum.selfhtml.org/self/2019/oct/19/unterschiedliche-logisch-beziehungen-in-einer-db-tabelle-speichern/1759045#m1759045 wKovacs 2019-10-20T11:48:07Z 2019-10-20T11:48:07Z unterschiedliche logisch Beziehungen in einer DB-Tabelle speichern <p>Vielen Dank für die Hinweise und Vorschläge und erst recht für die aufgewendete Zeit.</p> <p>Ich werde experimentieren und sehen wohin es mich führt</p> https://forum.selfhtml.org/self/2019/oct/19/unterschiedliche-logisch-beziehungen-in-einer-db-tabelle-speichern/1759092#m1759092 Rolf B 2019-10-21T08:35:48Z 2019-10-21T08:35:48Z unterschiedliche logisch Beziehungen in einer DB-Tabelle speichern <p>Hallo Camping_RIDER,</p> <p>sorry, hatte wohl Knöpfe auf den Augen. Klar - binäre Terme kann man als binären Baum aufbauen und per SQL rekursiv zusammensuchen. Dagegen steht dann alternativ mein Vorschlag mit der DNF und einem n-ären zweistufigen Baum, der sich ohne Rekursion auslesen lässt. Letztendlich hast Du ja nur eine Klammer mehr gesetzt (und dich bei KursD vertippt )</p> <p>wKovacz: KursX = KursA UND (KursB ODER (KursC UND KursD) ODER KursE)</p> <p>CampRid: KursX = KursA UND (KursB ODER (KursE ODER (KursC UND KursD)))</p> <p>Das sind 5 Kurse, die Wahrheitstabelle ist demnach etwas umständlicher. Der Term ist hier aber so gestaltet, dass die DNF relativ einfach zu finden ist. Man muss das UND hinter KursA nur ausmultiplizieren und bekommt (boolescher Term, UND wird nicht geschrieben und $$\lor$$ (lat. vel = oder) steht für ODER. Ein NOT würde als $$\overline{A} $$ geschrieben). Sei X die Regel für Kurs X und ABCDE die Kurse A-E. Dann sieht euer mehrstufiger Term als DNF so aus:</p> <p>$$X = AB \lor ACD \lor AE$$</p> <p>Im Allgemeinen ist das Finden der DNF bei verschachtelten Termen umständlicher, aber da ist auch das Schreiben des Terms umständlich, und es ist einfacher, von der Wahrheitstabelle auszugehen. Um dann aus einer Wahrheitstabelle eine optimale DNF zu bauen, gibt es Techniken (Karnaugh-Veitch-Diagramm und Quine-McCluskey Algorithmus) und bestimmt auch Tools (wobei ich gerade keins finde, das eine Wahrheitstafel als Input nimmt - seltsam).</p> <p>Wenn das zu kompliziert ist - eine optimierte DNF ist nicht zwingend nötig. Auf sowas reiten die Schaltalgebra-Ingenieure herum, bei denen unnötige Siliziumatome oder Quadratnanometer Geld richtig teuer sind.</p> <p>In den von mir vorgeschlagenen Tabellen sähe es so aus:</p> <p><strong>OderTerme</strong></p> <pre><code class="block">Kurs Gruppe KursX 201 KursX 202 KursX 203 </code></pre> <p><strong>UndTerme</strong></p> <pre><code class="block">Gruppe Vor_Kurs Erforderlich 201 KursA 1 201 KursB 1 202 KursA 1 202 KursC 1 202 KursD 1 203 KursA 1 203 KursE 1 </code></pre> <p><em>Rolf</em></p> <div class="signature">-- <br> sumpsi - posui - clusi </div> https://forum.selfhtml.org/self/2019/oct/19/unterschiedliche-logisch-beziehungen-in-einer-db-tabelle-speichern/1759079#m1759079 Email https://rolfrost.de/dbiutf8.html 2019-10-21T05:54:19Z 2019-10-21T05:54:19Z unterschiedliche logisch Beziehungen in einer DB-Tabelle speichern <blockquote> <p>Vielen Dank für die Hinweise und Vorschläge und erst recht für die aufgewendete Zeit.</p> </blockquote> <p>Keine Ursache. Mit meinen Kochrezepten ergibt sich dieselbe Problemstellung: Anhand eines Kochrezept berechnen, welche Zutaten drin sind. Und da hab ich, dank Deines POST gestern endlich mal so richtig drüber nachgedacht wie ich das machen könnte </p> <p>MFG</p> https://forum.selfhtml.org/self/2019/oct/19/unterschiedliche-logisch-beziehungen-in-einer-db-tabelle-speichern/1759098#m1759098 Camping_RIDER janosch.zoller@selfhtml.org http://www.campingrider.de 2019-10-21T09:39:56Z 2019-10-21T09:39:56Z unterschiedliche logisch Beziehungen in einer DB-Tabelle speichern <p>Aloha ;)</p> <blockquote> <p>sorry, hatte wohl Knöpfe auf den Augen. Klar - binäre Terme kann man als binären Baum aufbauen und per SQL rekursiv zusammensuchen.</p> </blockquote> <p>Ja. Ich sagte ja auch bereits, dass mein Vorschlag halt eine Möglichkeit ist, das darzustellen, dass ich mir aber nicht sicher bin, ob das Datenmodell für eine relationale Datenbank optimal ist. Die Rekursion ist ein negativer Aspekt (denn SQL-Auswertung geht damit nicht), und...</p> <blockquote> <p>Dagegen steht dann alternativ mein Vorschlag mit der DNF und einem n-ären zweistufigen Baum, der sich ohne Rekursion auslesen lässt.</p> </blockquote> <p>...dein DNF-Vorschlag ist sicher besser für die relationale Datenbank optimiert. Mir leuchtet dein Vorschlag daher total ein.</p> <p>Problematisch dabei ist, aber das schriebst du ja selbst, dass es ggf. ein größerer Aufwand ist, die DNF zu finden, bzw. das für einen allgemeinen Fall zu implementieren.</p> <p>Man muss da halt abwägen: Möchte man die Abbildung mit Rekursion, die beim Auslesen / Anwenden nicht alleine mit SQL funktioniert, sondern beim Auslesen ein rekursives Vorgehen benötigt, oder möchte man die rekursionsfreie Abbildung, die beim Speichervorgang / Implementieren einen großen Aufwand bedeutet.</p> <p>Kommt es nicht so sehr auf die Performance beim Auslesen an, z.B. weil man das nicht so häufig prüfen muss, würde ich meine Idee bevorzugen - weil sie so schön einfach und nah an der intuitiven Überlegung ist.</p> <p>Kommt es hingegen auf die Performance beim Auslesen an, z.B. weil man das häufig prüfen muss, ist deine Idee zu bevorzugen - denn sie erfordert beim Implementieren Aufwand und Umgehen (du hast die Idee zwar umrissen, aber bis zum konkreten Algorithmus ist es noch ein gewisser Weg), ist aber in der Anwendung der gespeicherten Regeln sehr effizient.</p> <blockquote> <p>Letztendlich hast Du ja nur eine Klammer mehr gesetzt (und dich bei KursD vertippt )</p> </blockquote> <p>Ups. </p> <hr> <p>TL;DR: Mir gefällt deine Lösung vom fachlichen Standpunkt sehr gut. Sie ist gut optimiert und deutlich sauberer / systematischer als meine. Implementieren würd ich sie aber nicht unbedingt wollen </p> <p>Grüße,</p> <p>RIDER</p> <div class="signature">-- <br> Camping_RIDER a.k.a. Riders Flame a.k.a. Janosch Zoller<br> # <a href="https://twitter.com/Camping_RIDER" rel="nofollow noopener noreferrer">Twitter</a> # <a href="http://steamcommunity.com/id/Camping_RIDER" rel="nofollow noopener noreferrer">Steam</a> # <a href="https://www.youtube.com/user/RidersFlame" rel="nofollow noopener noreferrer">YouTube</a> # <a href="http://wiki.selfhtml.org/wiki/Benutzer:Camping_RIDER" rel="nofollow noopener noreferrer">Self-Wiki</a> # <a href="http://community.de.selfhtml.org/fanprojekte/selfcode.htm" rel="nofollow noopener noreferrer">Selfcode</a>: sh:) fo:) ch:| rl:) br:^ n4:? ie:% mo:| va:) js:) de:> zu:} fl:( ss:) ls:[ </div> https://forum.selfhtml.org/self/2019/oct/19/unterschiedliche-logisch-beziehungen-in-einer-db-tabelle-speichern/1759099#m1759099 Email https://rolfrost.de/dbiutf8.html 2019-10-21T09:40:24Z 2019-10-21T09:40:24Z unterschiedliche logisch Beziehungen in einer DB-Tabelle speichern <blockquote> <p>sorry, hatte wohl Knöpfe auf den Augen. Klar - binäre Terme kann man als binären Baum aufbauen und per SQL rekursiv zusammensuchen. Dagegen steht dann alternativ mein Vorschlag mit der DNF und einem n-ären zweistufigen Baum, der sich ohne Rekursion auslesen lässt. Letztendlich hast Du ja nur eine Klammer mehr gesetzt (und dich bei KursD vertippt )</p> </blockquote> <p>Genau! Das Ganze lässt sich linear und ohne Rekursion lösen. Allerdings braucht es dafür eine Bedingung: Die Anzahl der Kurse muss endlich sein. Eine Bedingung die sich zweifelsfrei erfüllen läßt </p> <p>Meine Lösung ist soweit fertig, ich werd' sie demnächst vorstellen.</p> <p>MFG</p> https://forum.selfhtml.org/self/2019/oct/19/unterschiedliche-logisch-beziehungen-in-einer-db-tabelle-speichern/1759100#m1759100 Camping_RIDER janosch.zoller@selfhtml.org http://www.campingrider.de 2019-10-21T09:44:45Z 2019-10-21T09:44:45Z unterschiedliche logisch Beziehungen in einer DB-Tabelle speichern <p>Aloha ;)</p> <blockquote> <p>Genau! Das Ganze lässt sich linear und ohne Rekursion lösen.</p> </blockquote> <p>Ja. Wie Rolf B ja bereits schrieb.</p> <blockquote> <p>Meine Lösung ist soweit fertig, ich werd' sie demnächst vorstellen.</p> </blockquote> <p>Du könntest, so du wirklich was beitragen willst, erläutern, inwiefern die von Rolf B's Vorschlag abweicht und warum sie an der Stelle dann optimaler ist. Ich bin gespannt.</p> <p>Grüße,</p> <p>RIDER</p> <div class="signature">-- <br> Camping_RIDER a.k.a. Riders Flame a.k.a. Janosch Zoller<br> # <a href="https://twitter.com/Camping_RIDER" rel="nofollow noopener noreferrer">Twitter</a> # <a href="http://steamcommunity.com/id/Camping_RIDER" rel="nofollow noopener noreferrer">Steam</a> # <a href="https://www.youtube.com/user/RidersFlame" rel="nofollow noopener noreferrer">YouTube</a> # <a href="http://wiki.selfhtml.org/wiki/Benutzer:Camping_RIDER" rel="nofollow noopener noreferrer">Self-Wiki</a> # <a href="http://community.de.selfhtml.org/fanprojekte/selfcode.htm" rel="nofollow noopener noreferrer">Selfcode</a>: sh:) fo:) ch:| rl:) br:^ n4:? ie:% mo:| va:) js:) de:> zu:} fl:( ss:) ls:[ </div>