[Funktion] Rekursive Darstellung (mal wieder)

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

  • [Funktion] Rekursive Darstellung (mal wieder)

    Hallo,

    Ich hänge hier beim Praktikum grad an inem Problem. Ich habe eine ganz einfache Tabelle für Kategorien angelegt, die hat die felder "katid", "overid", "name", "description".

    Ich will bei meinem script jetzt die Kategorien, samt Unterkategorien, in der Art anzeigen lassen:

    Kategorie 1
    -Unterkategorie1
    -Unterkategorie2
    --bla1
    --bla2
    ---blablub.

    etc.
    overid enthält die parentId also die übergeordnete Kategorie.
    Ich habe schonmal vorgarbeitet und folgende Funktion erstellt:
    PHP-Code:
    function getCat($overId)
    {
        global 
    $db;
        
    $subCat = array();
        if(
    $overId != "")
        {
            
    $underkat $db->query("SELECT * FROM ccc_kategorie WHERE overid = ".$overId." ORDER BY katid DESC");
            
    $anzahl $db->num_rows("SELECT * FROM ccc_kategorie WHERE overid = ".$overId."");
        } else {
            
    $underkat $db->query("SELECT * FROM ccc_kategorie WHERE overid = 0 ORDER BY katid DESC");
            
    $anzahl $db->num_rows("SELECT * FROM ccc_kategorie WHERE overid = 0");
        }
        if(
    $anzahl != 0)
        {
            
    $i=0;
            while(
    $row $db->fetch_array($underkat))
            {
                
    $subCat[$i] = array();
                
    $subCat[$i]['katid'] = $row['katid'];
                
    $subCat[$i]['overid'] = $row['overid'];
                
    $subCat[$i]['name'] = $row['name'];
                
    $subCat[$i]['desciption'] = $row['desciption'];
                
    $i++;
            }
        }
        return 
    $subCat;

    Jetzt weiß ich, dass ich eine weitere Funktion erstellen muss, welche sich rekursiv aufruft. Ich bleibe aber bei der Umsetzung dessen hängen.
    Nachher will ich ein array haben, welches in der richtigen Reihenfolge (also alle Kategorien auf dem gleichen Level sind nach dem Alphabet geordnet) alle Kategorien entält, samt einer Tiefe damit ich die Zeile gemäß der Tiefe einrücken kann.
    Wär nett wenn ihr mir eben helfen könntet.

    MfG Oli

  • #2
    hm... da ich noch keine Antwort erhalten habe...

    Ich formuliere es mal allgemeiner:

    Ich habe eine Tabelle mit Kategorien. Unter anderem ist eine id und eine parentid vorhanden.

    Wie bekomm ich es jetzt hin, dass ich nachher ein array mit den einzelnen Kategorien und einer Zahl, welche die Tiefe der Verschachtelung angibt, habe?

    Mir ist klar, dass es sich um eine Rekursion handelt, aber wie ich das bewekstelligen soll, weiß ich nicht.

    Kommentar


    • #3
      Hm... andererseits frage ich mich, warum du nicht selbst drauf kommt, da du die Tabelle selbst angelegt hast, müsstest du eigentlich vorher wissen wie man dann an die Daten kommt. Man legt doch keine Tabellenstruktur einfach so fest

      Du kannst entweder mit JOIN und Group By die Daten holen und einfach so ausgeben. Oder du schreibst eine Funktion, die die Sublemente ausgibt und gleichzeitig prüft, ob Subsubelemente existieren und bei Bedarf sich selbst aufruft (rekursiv). Denkt einfach an das Verzeichnissystem auf jedem Rechner; ich glaube, Ansätze dazu müsstest du hier im Forum auch finden.
      Zuletzt geändert von asp2php; 10.05.2004, 16:16.

      Kommentar


      • #4
        Original geschrieben von OliOli
        hm... da ich noch keine Antwort erhalten habe...
        das ist zwar ungewöhnlich nach 5 stunden noch keinen antwort zu haben, aber 1-2 tage solltest du uns schonmal zeit geben, bis du deinen thread wieder einem push unterziehst.....
        INFO: Erst suchen, dann posten![color=red] | [/color]MANUAL(s): PHP | MySQL | HTML/JS/CSS[color=red] | [/color]NICE: GNOME Do | TESTS: Gästebuch[color=red] | [/color]IM: Jabber.org |


        Kommentar


        • #5
          Ja ich weiß... Tut mir ja auch Leid...

          @asp2php: Sicher hab ich mir dabei was gedacht, und directory listening funktionen mit rekursivem AUfruf gehen mir auch leicht von der Hand.

          Aber aus unerfindelichen Gründen weiß ich nicht wie ich das mit der DB machen soll, denn da kommen Faktoren mit templates und lauter arrays dazu, die erstellt und erweitert werden müssen...

          Kommentar


          • #6
            so ich bin ein bisschen weiter. Ich hab jetzt ne funktion geschrieben, die eigentlich alles tun sollte.

            PHP-Code:
            function tree($overid=0$depth 0)
            {
                global 
            $db;
                if(
            $overid == 0)
                    
            $cat $db->query("SELECT * FROM ccc_kategorie WHERE overid = 0");
                else
                    
            $cat $db->query("SELECT * FROM ccc_kategorie WHERE overid = ".$overid);
                
            $i=0;
                while(
            $row $db->fetch_array($cat))
                {
                    
            $subCat = array();
                    
            $subCat[$i]['katid'] = $row['katid'];
                    
            $subCat[$i]['overid'] = $row['overid'];
                    
            $subCat[$i]['name'] = $row['name'];
                    
            $subCat[$i]['description'] = $row['description'];
                    
            $subCat[$i]['depth'] = $depth;
                    
            $subCount $db->num_rows("SELECT katid FROM ccc_kategorie WHERE overid = ".$overid);
                    if(
            $subCount 0)
                        
            tree($overid$depth+1);
                    
            $i++;
                }
                return 
            $subCat;

            dummerweise lädt sich das script tot... ich weiß nicht, wieso...

            Kommentar


            • #7
              dummerweise lädt sich das script tot... ich weiß nicht, wieso...
              Weil du die Funktion immer wieder mit der selben $overid aufrufst.
              Es werden also immer wieder die gleichen Daten aus der Datenbank geholt => Endlosschleife!!

              Du musst also vor deinem rekursiven Funtionsaufruf $overid einen neuen Wert zuweisen.
              Und zwar die id der aktuellen Kategorie (ich schatze mal $row['katid'])

              Kommentar


              • #8
                Original geschrieben von OliOli

                ...denn da kommen Faktoren mit templates und lauter arrays dazu, die erstellt und erweitert werden müssen...
                Ähm ... bei Templates muss ich passen, in diesem Bereich hab ich null Ahnung

                Kommentar


                • #9
                  PHP-Code:
                  function tree($overid 0$depth 0$i 0)
                  {
                      global 
                  $db;
                      
                  $rowCount $db->num_rows("SELECT katid FROM ccc_kategorie");
                      if(
                  $overid == 0)
                          
                  $cat $db->query("SELECT * FROM ccc_kategorie WHERE overid = 0");
                      else
                          
                  $cat $db->query("SELECT * FROM ccc_kategorie WHERE overid = ".$overid);
                      if(!isset(
                  $subCat)) $subCat = array();
                      while(
                  $row $db->fetch_array($cat))
                      {
                          echo 
                  $i;
                          
                  $subCat[$i]['katid'] = $row['katid'];
                          
                  $subCat[$i]['overid'] = $row['overid'];
                          
                  $subCat[$i]['name'] = $row['name'];
                          
                  $subCat[$i]['description'] = $row['description'];
                          
                  $subCat[$i]['depth'] = $depth;
                          
                  $subCount $db->num_rows("SELECT katid FROM ccc_kategorie WHERE overid = ".$overid);
                          
                  $i++;
                          if(
                  $subCount 0)
                              
                  tree($subCat[$i]['katid'], $depth++, $i);
                      }
                      if(
                  $i >= $rowCount)
                          
                  showArray($subCat);

                  Besten Dank, oppi. Nur hab ich das Gefühl, dass etwas mit dem $i noch nicht so ganz klappt, denn folgendes geht nicht:

                  Wenn ich das ganze aufrufe wird am Ende geprüft, ob $i der Anzahl der Datensätze entspricht, wenn ja wird mir das array ausgegeben.
                  Sollte es zumindest. Denn ich bekomme erstmal nur folgendes angezeigt:
                  0
                  Notice: Undefined offset: 1 in /var/www/html/webtoall/ccc/inc/functions.php on line 197
                  121
                  Notice: Undefined offset: 2 in /var/www/html/webtoall/ccc/inc/functions.php on line 197
                  23
                  (die zahlen wegen dem echo $i
                  Zeile 197 ist die Zeile mit dem erneuten Aufruf der Funktion.

                  Ein array wird nich angezeigt, es sei denn ich überprüfe das Ende mit "if($i >= $rowCount-1)"

                  Also ich hab das Gefühl, dass etwas mit dem $i oder des Arrays nicht stimmt.

                  MfG Oli

                  Kommentar


                  • #10
                    überlege doch mal, was bei Rekursionsaufruf passiert.
                    Oder wenn du einen Debugger hast, kannst du mal Breakpoint setzen, dann kannst du mal die Werte vor dem Rekursionaufruf, im Rekursionsablauf und nach Rekursionsaufruf ablesen, dann wird dir schon klar

                    Kommentar


                    • #11
                      hm zuerst machst du
                      PHP-Code:
                      $subCat[$i]['katid'] = $row['katid']; 
                      dann machst du
                      PHP-Code:
                      $i++ 
                      und dann
                      PHP-Code:
                      tree($subCat[$i]['katid'], $depth++, $i); 
                      Welchen wert glaubst du hat $subCat[$i]['katid'] im Funktionsaufruf?

                      Kommentar


                      • #12
                        /edit

                        meine aktuelle funktion nochmal und fehlerbeschreibung

                        PHP-Code:
                        function tree($overid 0$depth 0$i 0)
                        {
                            global 
                        $db;
                            
                        $rowCount $db->num_rows("SELECT katid FROM ccc_kategorie");
                            if(
                        $overid == 0)
                                
                        $cat $db->query("SELECT * FROM ccc_kategorie WHERE overid = 0");
                            else
                                
                        $cat $db->query("SELECT * FROM ccc_kategorie WHERE overid = ".$overid);
                            if(!isset(
                        $subCat)) $subCat = array();
                            while(
                        $row $db->fetch_array($cat))
                            {
                                echo 
                        $i;
                                
                        $subCat[$i]['katid'] = $row['katid'];
                                
                        $subCat[$i]['overid'] = $row['overid'];
                                
                        $subCat[$i]['name'] = $row['name'];
                                
                        $subCat[$i]['description'] = $row['description'];
                                
                        $subCat[$i]['depth'] = $depth;
                                
                        $subCount $db->num_rows("SELECT katid FROM ccc_kategorie WHERE overid = ".$subCat[$i]['katid']);
                                
                        $i++;
                                if(
                        $subCount 0)
                                    
                        tree($row['katid'], $depth++, $i);
                            }
                            if(
                        $i >= $rowCount-1)
                                
                        showArray($subCat);

                        Es wird mir jetzt kein array oder so mehr ausgegeben. Ich bekomme lediglich die Zahlen 01212 angezeigt, welche $i entsprechen. Die Funktion läuft also schonmal 5 al durch, nur $i stimmt eben nicht.
                        Zuletzt geändert von OliOli; 11.05.2004, 09:57.

                        Kommentar


                        • #13
                          wenn du Window OS hast, lade mal den phpedit unter www.phpedit.net runter. Der hat einen guten Debugger.
                          Andererseits ist es denn so schwer, ein paar Ablaufschritte zu illustrieren, alles was man dazu braucht, ist einen Stift und ein Blatt Papier

                          Kommentar


                          • #14
                            hm, ich habs mal mit stift und zettel gemacht

                            Also ich weiß wieso $i falsch definiert wird...

                            ich versuch mal das zu erklären.
                            erster Durchlauf, $i ist 0 und alles klappt wunderbar, $i wird um einen erhöht.
                            Die Funktion erkennt, es gibt unterkategorien und ruft sich selbst auf. Alles klappt, $i bekommt den Wert 2. Das ganze geschieht mit noch einer Unterkategorie, $i sollte jetzt also 3 sein.

                            Allerdings sind die Unterkategorien zu ende und die Ursprungsschleife läuft weiter - in der $i noch den Wert 1 besitzt...

                            Wie mach ich aus einer Unterschleife den Wert auch für die übergeordneten Schleifen gültig? Mir fällt im Moment nur der Weg über sessions ein, aber das scheint mir eine sehr schlechte Lösung zu sein.

                            Achja, sorry wenn ich etwas schwer von begriff bin, ich kann kaum php...

                            Kommentar


                            • #15
                              zum Glück gibts bei Funktionen in php sowas wie einen rückgabewert, den man mit return angeben kann

                              Kommentar

                              Lädt...
                              X