Ankündigung

Einklappen
Keine Ankündigung bisher.

Einen Zeilen-Komplex zu Spalten machen

Einklappen

Neue Werbung 2019

Einklappen
X
  • Filter
  • Zeit
  • Anzeigen
Alles löschen
neue Beiträge

  • Einen Zeilen-Komplex zu Spalten machen

    Hi,
    ich versuche mir gerade etwas die Möglichkeiten vom SQL zu erschließen
    und hatte irgend wann die Idee zu erkunden, ob man auch auf alternative Art
    und Weise eine Matrix zusammenstellen kann.

    Höchstwahrscheinlich wird der Ansatz euch total absurt vorkommen
    und ggf. "sinnfrei" oder "unperformant" sein,
    allerdings würde er für mich sehr viel Erkenntnis bedeuten.

    Ich würde mich sehr freuen wenn Ihr euch drauf einlassen würdet
    und helfen möchtet meinem Ziel ein Stück näher zu kommen.

    Ich habe in meiner Datenbank 3 Tabellen:

    - Tabelle "info" speichert Informationen wie z. B. eine Telefonnummer.
    - Tabelle "object" speichert Datensätze als Ankerpunkt für ggf. mehrer Informationen und charakterisiert diese Objekt z. B. als Kunden.
    - Tabelle "relation" stellt die Verbindung zwischen einem Objekt und einer Information her (1:1, 1:n, n:m)

    Meine Datenbank sieht wie folgt aus:
    PHP-Code:
    CREATE  TABLE IF NOT EXISTS `ROD`.`object` (
      `
    idINT NOT NULL AUTO_INCREMENT ,
      `
    stateTINYINT(1)  NOT NULL ,
      
    PRIMARY KEY (`id`) )
    ENGINE MyISAM;

    CREATE  TABLE IF NOT EXISTS `ROD`.`info` (
      `
    idINT NOT NULL AUTO_INCREMENT ,
      `
    metaVARCHAR(64NOT NULL ,
      `
    dataVARCHAR(1024NOT NULL ,
      `
    stateTINYINT(1)  NOT NULL ,
      
    PRIMARY KEY (`id`) )
    ENGINE MyISAM;

    CREATE  TABLE IF NOT EXISTS `ROD`.`relation` (
      `
    idINT NOT NULL AUTO_INCREMENT ,
      `
    roottblVARCHAR(64NOT NULL ,
      `
    rootidVARCHAR(64NOT NULL ,
      `
    targettblVARCHAR(64NOT NULL ,
      `
    targetidVARCHAR(64NOT NULL ,
      `
    stateTINYINT(1)  NOT NULL ,
      
    PRIMARY KEY (`id`) )
    ENGINE MyISAM;

    INSERT INTO `object` (`id`, `state`) VALUES
    (1'1'1),
    (
    2'2'1);

    INSERT INTO `info` (`id`, `meta`, `data`, `state`) VALUES
    (1'kundennummer''500001'1),
    (
    2'anrede''1'1),
    (
    3'titel''Bsc.'1),
    (
    4'vorname''Hans'1),
    (
    5'nachname''Wurst'1),
    (
    6'strasse''Auf dem Holzweg'1),
    (
    7'hausnummer''1a'1),
    (
    8'kundennummer''500002'1),
    (
    9'anrede''1'1),
    (
    10'vorname''Bäm'1),
    (
    11'nachname''Lee'1),
    (
    12'strasse''Over The Rainbow'1),
    (
    13'hausnummer''6'1);

    INSERT INTO `relations` (`id`, `roottbl`, `rootid`, `targettbl`, `targetid`, `state`) VALUES
    (1'object'1'info'11),
    (
    2'object'1'info'21),
    (
    3'object'1'info'31),
    (
    4'object'1'info'41),
    (
    5'object'1'info'51),
    (
    6'object'1'info'61),
    (
    7'object'1'info'71),
    (
    8'object'2'info'81),
    (
    9'object'2'info'91),
    (
    10'object'2'info'101),
    (
    11'object'2'info'111),
    (
    12'object'2'info'121),
    (
    13'object'2'info'131),
    (
    14'object'2'info'141); 
    Nun möchte ich die Phrase konstruieren, die mich zu folgender Ergebnis-Tabelle führt:

    PHP-Code:
    ===========================================================================================
    |  
    kundennummer  |  anrede  |  titel  |  vorname  |  nachname  |  strasse  |  hausnummer  |
    ===========================================================================================
    |  
    500001        |  1       |  Bsc.   |  Hans     |  Wurst     |  Auf[...] |  1a          |
    |  
    500002        |  1       |         |  Bäm      |  Lee       |  Ove[...] |  6           |
    =========================================================================================== 
    Bisher bin ich mit folgenden Phrasen nur bedingt nah an mein Ergebnis gekommen:
    PHP-Code:
        SELECT object.iddata.metadata.data
        FROM object
        RIGHT JOIN 
            relation 
    AS forthtrace ON object.id=forthtrace.targetid
        RIGHT JOIN 
            info 
    AS data ON forthtrace.rootid=data.id
        WHERE object
    .id=forthtrace.targetid 
    Das Ergenis des Querys bildet allerdings nicht die verschiedenen Infos als Spalten ab, sondern nur als Zeilen - Aber zugeordnet.
    Wie bekomme ich denn das jetzt noch alles zu einer Zeile kumuliert?

    Habt Ihr ne Idee?
    Vielen Dank schonmal im Voraus!

  • #2
    Die Struktur ist bekannt. Man kann in einer Tabelle "Spalten" dazuerfinden, indem man einfach zu einer id einer Stammtabelle neue Zeilen dazuschreibt. Dabei braucht man allerdings keine verbindende Tabelle, sondern es reicht, die ID der Stammtabelle mit in die Zeile zu legen.
    Der Nachteil liegt darin, dass die Spaltentypen für die Werte immer varchar sein müssen und man auf die Vorteile, die z.B. datetime bietet verzichtet. Für die meisten Anwendungsfälle bietet das m.E. keinerlei Vorteile.
    [PHP]if ($var != 0) {
    $var = 0;
    }[/PHP]

    Kommentar


    • #3
      Okay, nochmal in meinen Worten:
      - Das Modell ist gängig und nicht total absurd?
      - Ich kann die Zeilen zu spalten machen
      - Man brach dafür nicht gezwungenermaßen eine Relations-Tabelle
      - Absolut alle Spalten müssen "varchar" sein

      Und gemäß des Falles das ich eine Relations-Tabelle haben möchte würde das "in Action" wie genau aussehen? Mir Harpers u.a. auch an der Syntax von SQL.

      Vielen Dank schonmal!

      Kommentar


      • #4
        mySQL-Tabelle transponieren

        Hi, ich steuer schon den ganzen Tag durchs Web und versuche ein paar Bruchstücke zu finden um mein Problem von
        dem gestern geposteten Thema "Einen Zeilen-Komplex zu Spalten machen" zu lösen.

        Das was ich gerade händeringend suche, ist das Feature mit dem ich unter mySQL eine Tabelle transponieren kann bzw. meine Zeilen zu Spalten umforme.

        Wie ich gemerkt habe, gibt es im Web herrlich viele Einträge von Leuten die das gleiche Problem haben.

        Allerdings werden bei den Forenbeiträgen das Ganze so konkret abhandelt, das ich es mit meinen sehr limitierten Erfahrungen in nicht auf mein Problem übertragen bekomme.

        Problem ist auch, dass ich aus dem folgenden Konstrukt interpretiere, dass mir von vornherein klar sein muss auf welche und wie viele Spalten ich heraus möchte.

        Code:
        // Tabelle1 
        ------------------------------ 
        | ID | Vorn.   | Nachname    | 
        ------------------------------ 
        | 01 | Max     | Mustermann  | 
        | 02 | Lila    | Lustig      | 
        | 03 | Florian | Fröhlich    | 
        |----------------------------| 
        
        // Tabelle2 
        ------------------------------- 
        | Nr | Bez.     | Wert        | 
        ------------------------------- 
        | 01 | Tel.     | 111111111   | 
        | 02 | Handy    | 999999999   | 
        | 03 | Mail     | la@web.de   | 
        | 04 | Tel.     | 222222222   | 
        | 05 | Tel.     | 333333333   | 
        | 06 | Mail     | uf@gmx.de   | 
        | 07 | Geb.     | 13.05.1964  | 
        | 08 | Handy    | 888888888   | 
        |-----------------------------| 
        
        // Tabelle3 
        ------------ 
        | Nr | ID  | 
        ------------ 
        | 01 | 01  | 
        | 02 | 03  | 
        | 03 | 02  | 
        | 04 | 02  | 
        | 05 | 03  | 
        | 06 | 03  | 
        | 07 | 03  | 
        | 08 | 01  | 
        |----------|
        
        // Wird das gewünschte Ergebnis
        --------------------------------------------------- 
        | Vorn.   | Nachname    |    Tel.   |   Handy     | 
        --------------------------------------------------| 
        | Max     | Mustermann  | 111111111 | 888888888   | 
        | Lila    | Lustig      | 222222222 |             | 
        | Florian | Fröhlich    | 333333333 | 999999999   | 
        |------------------------------------------------ |
        
        // mit dieser Phrase abgefragt
        SELECT T1.*, Q1.Wert AS [Tel], Q2.Wert AS [Handy] 
        FROM   (Tabelle1 AS T1 
                LEFT JOIN (SELECT T3.ID, T2.Wert 
                           FROM   Tabelle2 AS T2 
                                  INNER JOIN Tabelle3 AS T3 
                                  ON T2.Nr = T3.Nr 
                           WHERE  T2.Bez='Tel.') AS Q1 
                ON T1.ID = Q1.ID) 
               LEFT JOIN (SELECT T3.ID, T2.Wert 
                          FROM   Tabelle2 AS T2 
                                 INNER JOIN Tabelle3 AS T3 
                                 ON T2.Nr = T3.Nr 
                          WHERE  T2.Bez='Handy') AS Q2 
               ON T1.ID = Q2.ID
        Das was mich an diesem Modell jedoch reizt, ist die Möglichkei, Spalten-Namen und Spalten-Menge komplex zu lassen.

        Ich suche naiver Weise nach einer abstrakten Methode für soetwas:
        Code:
        TRANSPOSE SELECT * FROM tbl
        Ich zweifle

        Kommentar


        • #5
          *zusammenführ*

          Bitte unterlasse es künftig, neue Threads zu eröffnen, wenn die Thematik immer noch die gleiche ist.
          [SIZE="1"]RGB is totally confusing - I mean, at least #C0FFEE should be brown, right?[/SIZE]

          Kommentar


          • #6
            Wozu brauchst du das noch gleich?
            allerdings würde er [der Ansatz] für mich sehr viel Erkenntnis bedeuten.
            In welcher Hinsicht?
            [URL]http://hallophp.de[/URL]

            Kommentar


            • #7
              Für mich würde es bedeuten, dass ich ein DB-Modell hätte in dem ich alle meine Projekte abbilden kann, ohne mir über die Anzahl und den Aufbau der Tabellen und z. B. Foreign Keys Gedanken machen müsste.

              Ich abstrahiere alle Informations-Sets auf die Denkweise: Object, Info, Relation - Egal ob es um eine Kunden-Tabelle, Rechnungsposten, Emails, Dokumente oder was auch immer geht.

              Ob das Modell dann auch genug Performance bringt, ist dann eine andere, ökonomische Abwegung zwischen potenzieller Datenlast und Einrichtungs-Aufwand bzw. Konzeption der DB.

              Ich bin auch nicht versteift dieses Modell unbedingt praktikabel zu machen, ich versuch mich zu orientieren, weil ich es so dermaßen lästig finde immer aufs neue DBs zu gestalten.

              Ich suche nicht nach Lösungen für einen Speziellen Fall, ich suche nach weniger Arbeit mit DBs.

              Kommentar


              • #8
                Hi, ich bin gerade wirklich aufgeschmissen, weil ich google mich tot,
                es sind leider Semesterferien und bei mir in der Fakultät niemand ansprechbar.

                Ich habe jetzt gestern mit einem wirklich kompetenten PHP-Kollegen gesprochen,
                der grundsätzlich erstmal meinte, dass ich mir darüber klar werden sollte,
                ob mySQL dazu überhaupt fähig ist.

                Kurzer Hand habe ich mich mal schau gemacht und auch andere DBMS mir angeschaut.

                Ich habe z. B. unter postgreSQL eine "tablefunction" namens "crosstab" gefunden,
                die angeblich es ermöglichen soll Zeilen zu Spalten zu machen.

                Leider bin ich auch da an 2 Problemen gescheitert:
                - die "tablefunction" "crosstab" ist nicht standardmäßig in der Bibliothek von postgreSQL enthalten
                - "crosstab" kann nicht auf dynamische bzw. komplexe Art und Weise eine unbestimmte Anzahl an Zeilen zu Spalten zu machen.

                Da es sich hier aber eigentlich um ein gängiges mathematisches Phänomen handelt, hab ich mal weiter geschaut:

                Ich hab unter dem Suchbegriff "Pivot" auch hier im Forum nur allgemeine Ratlosigkeit gefunden.

                Sehr enttäuschend, da der Begriff "Pivot" nicht nur ein zentraler Punkt des lineareren Algebra ist,
                sondern Pivot-Tabellen aus z. B. Microsoft Excel und der allgemeinen Theorie von Anwendungssystemen nicht wegzudenken ist.

                Ist das wirklich jetzt so, dass es schirr nicht geht?
                Und keiner davon Ahnung hat?
                Oder mir sagen kann, dass man es ggf. über mySQL-Methoden regeln könnte?

                Kommentar

                Lädt...
                X