Jörg: do while Schleife am Dateiende beginnen, nicht am -anfang

Hallo,

ich möchte eine Datei mit einer do/while/Schleife durchsuchen lassen, jedoch nicht vom Dateianfang sondern vom Dateiende aus, da ich die jüngsten Datensatz benötige, nicht den ältesten.

Danke für Eure Hilfe
Jörg

  1. Moin Moin !

    1. Zeilenweise in ein Array lesen und das von hinten durchforsten
    2. /usr/bin/tac benutzen http://www.google.com/search?q=tac+man+page (Tip: tac ist cat rückwärts ...)
    3. Hilfsdatei mit Offsets der Zeilenenden mitführen und pflegen, fseek und ftell benutzen.

    Alexander

    --
    Nein, ich beantworte keine Fragen per eMail. Dafür ist das Forum da.
    Today I will gladly share my knowledge and experience, for there are no sweeter words than "I told you so!"
    1. Ciao Alexander,

      DAU am Werk :-)
      Kannst Du mir das bitte nochma innerhal diesen Kontextes begreiflich machen?
      THX!!!

      http://forum.de.selfhtml.org/?t=41257&m=225608

      1. Hallo,

        http://forum.de.selfhtml.org/?t=41257&m=225608

        Du hast da folgendes stehen:

        $file = file("log.txt");
          for($i=0; $i < count($file); $i++) {

        ändere doch einfach die Schleife ab:

        for($i=count($file) - 1; $i >= 0; $i--) {

        Dann wird das Array File von hinten durchsucht. Oder du lässt die Schleife so wie sie ist und änderst die Zuweisung des Arrays ab:

        $file = array_reverse(file("log.txt"));

        Wieso schreibst du im Subject von einer do while Schleife? Welche Lösung würdest du denn gerne einsetzen?

        Viele Grüße,

        Stefan

        1. Hey Stefan,

          das erste Script im Posting http://forum.de.selfhtml.org/?t=41257&m=225608 ist von mir, welches aber von annA eben überarbeitet wurde, darauf baue ich auch auf, das sieht nun eben nachdem ich nochmals drüber bin so aus:

          <?php
          $user = $_SERVER["REMOTE_USER"];

          $i = -1;
          $file = file("logs/access.txt");
          do{
            $i++;
          }while((!(preg_match ("/\b$user\b [(.*) +/",
           $file[$i],$arr)) && $i < count($file)));

          if ($arr[1] == "") {
           $ausgabe = "(noch nie)";
          } else {

          $date_alt = substr($arr[1],0,11);
           $time_alt = substr($arr[1],12,8);
           $date_alt = str_replace("/"," ",$date_alt);
           $date_alt = str_replace("Jan","Januar",$date_alt);
           $date_alt = str_replace("Feb","Februar",$date_alt);
           $date_alt = str_replace("Mar","März",$date_alt);
           $date_alt = str_replace("Apr","April",$date_alt);
           $date_alt = str_replace("May","Mai",$date_alt);
           $date_alt = str_replace("Jun","Juni",$date_alt);
           $date_alt = str_replace("Jul","Juli",$date_alt);
           $date_alt = str_replace("Aug","August",$date_alt);
           $date_alt = str_replace("Sep","September",$date_alt);
           $date_alt = str_replace("Oct","Oktober",$date_alt);
           $date_alt = str_replace("Nov","November",$date_alt);
           $date_alt = str_replace("Dec","Dezember",$date_alt);

          $ausgabe = "Am $date_alt um $time_alt Uhr.<br>";
          }

          echo "$ausgabe";
          ?>

          das hat für mich nur das Prob, dass es die Datei von oben nach unten durchgeht und nicht umgekehrt.
          Was ich will ist anhand des LogFiles den letzten LogIn des Users zu erfahren, dieses Script gibt mir aber den ersten Besuch aus...
          Eine do while Schleife, um nicht das ganze Logfile zu durchforsten, sondern nach dem jüngsten Zugriff des Users abzubrechen um lange Ladezeiten zu vermeiden.
          Hier ein Beispiel einer Zeile des Logs:

          217.224.xxx.xx - user [10/Aug/2002:17:34:15 +0200] "GET / HTTP/1.1" 200 1863

          Thx und Gruß

          1. Servus Jörg!

            <?php
            $user = $_SERVER["REMOTE_USER"];

            $i = -1;
            $file = file("logs/access.txt");

            Hier setzt das erwähnte >> $file = array_reverse(file("log.txt")); << an. Durch den Aufruf von file() wird die Datei ja komplett in ein Array eingelesen. Mit array_reverse wird das ganze umgedreht. So steht dann in $file[0] die letzte Zeile der Datei.

            do{
              $i++;
            }while((!(preg_match ("/\b$user\b [(.*) +/",
            $file[$i],$arr)) && $i < count($file)));

            Währe ein

            for ($i = 0; $i < count($file); $i++) {
              preg_match ("/\b$user\b [(.*) +/", $file[$i], $arr) && break;
            }

            nicht schöner?

            Eine do while Schleife, um nicht das ganze Logfile zu durchforsten, sondern nach dem jüngsten Zugriff des Users abzubrechen

            Dafür sorgt in meinem Code das break.

            Viele Grüße,

            Stefan

            1. Ciao Stefan,

              also erst ma thx weg dem "array_reverse" das funzt nu.
              Aber mit dem Break das is nich so das wahre, bekomm nämlich nen Fehler -> Parse error: parse error, unexpected T_BREAK in x:\xx.php on line 11

              Hatte zuvor ja auch mit break gearbeitet, sort war meine variable aber immer leer *nerv*

              OK, zumindest läuft es jetzt, ob mit "do while" oder "break" is mir eig egal, aber break sieht schpn besser aus ;-)

              Ev siehste ja nochma hier rein, CU

              1. Hallo Jörg,

                Aber mit dem Break das is nich so das wahre, bekomm nämlich nen Fehler -> Parse error: parse error, unexpected T_BREAK in x:\xx.php on line 11

                Oh. Woran das liegt weiß ich jetzt leider nicht. Möglich, dass PHP meine Konstruktion mit && nicht gefällt. Du kannst mal untenstehendes versuchen:

                for ($i = 0; $i < count($file); $i++) {
                  if (preg_match ("/\b$user\b [(.*) +/", $file[$i], $arr))
                    break;
                }

                Testen kann ich es hier leider nicht, da ich in PHP normalerweise nix programmiere.

                Viele Grüße,

                Stefan