phpbar.de logo

Mailinglisten-Archive

[php] Re: Regex

[php] Re: Regex

Martin Ramsch m.ramsch_(at)_computer.org
Fri, 19 Mar 1999 12:15:10 +0100


--cWoXeonUoKmBZSoM
Content-Type: text/plain; charset=iso-8859-1
Content-Transfer-Encoding: 8bit

Axel Tietje schrieb am Freitag, den 19. März 1999:
> Für ein Dokumentmanagement-System (PHP+mySQL) das ich gerade bastle,
> muß ich in einer RTF-Datei Platzhalter ersetzen.
[...]
> Cool wäre es auch, wenn der Substring 'Ablage' erkannt werden könnte
> und der Substring 'ABLAGE_TAG' dann durch den Wert einer Variable
> $property['Ablage'] ersetzt würde. Dann könnte man beliebige
> RTF-Properties verwenden.

Wenn Du beim Suchen-und-Ersetzen den Ersetzungstext von der Fundstelle
abhängig machen willst, gibt es meines Wissens in PHP eigentlich nur
eine Vorgehensweise:
  1.) Erst mit "eregi" prüfen, ob eine passende Fundstelle existiert.
      Dabei kann man sich gleich die einzelnen Teile der Fundstelle
      merken.
  2.) Da die Einzelteile jetzt verfügbar sind, kann man den Ersetzungs-
      text abhängig vom Gefundenen berechnen und dann mit
      "eregi_replace" passend einsetzen.

Wenn Du nicht nur die erste, sondern alle Fundstellen behandeln willst,
kommt das Ganze in eine Schleife, die solange läuft, bis "eregi" nichts
Passendes mehr findet.
Problem:  Wird eine Fundstellen durch "eregi_replace" nicht "genug"
          verändert, wird immer wieder diese gleiche Stelle gefunden -
          eine Endlosschleife!
Lösung:   Bei "eregi" auch gleich den gesamten Rest nach der Fundstelle
          als einen Teil merken.  Dann in der Schleife immer nur
          iterativ diesen Rest weiter-durchsuchen und -bearbeiten.

Jetzt fehlt nur noch eine große Schleife außenherum, die alle zu
suchenden Properies durchläuft - und Du bist fertig. :)


Was gibt's noch?

Strings:
  Ein Backslash in einem String = "\\" (so geht's immer).  Wenn das
  Zeichen nach dem Backslash keine Sonderbedeutung haben kann (die man
  mit dem Backslash aufheben könnte), wenn also quasi "klar" ist, daß
  man den Backslash selbst haben möchte, geht es z.B. auch so: "\a"
  "\{" "\}" ...
  Aber "\n" gibt ein Newline; "\\n" dagegen gibt Backslash En.

Reguläre Ausdrücke:
  Vor Zeichen mit Sonderbedeutung wie z.B. ( ) { } \ [ ] * . und so
  fort muß ein Backslash stehen, wenn sie wörtlich gemeint sein sollen.

Reguläre Ausdrücke als Strings hingeschrieben:
  Welcher reguläre Ausdruck sucht genau nach
  der Zeichenfolge "/* (c) Ramsch\x */"?
  Lösung: "/\* \(c\) Ramsch\\x \*/"

  Wie schreibt man das als realen PHP-String hin?
  Lösung: $a = "/\\* \\(c\\) Ramsch\\\\x \\*/";

  Oder:   $B=chr(92);
          $a = "/".$B."* ".$B."(c".$B.") Ramsch".$B.$B."x ".$B."*/"

> Ach ja, noch was: Wenn das RTF-File dann z. B. in Word97 bearbeitet
> wurde, werden natürlich Zeilenumbrüche im RTF-Source geändert. Das ganze
> müßte also auch über Zeilenumbrüche hinweg funktionieren.

Einfach immer dort, wo Du normalerweise nur auf Leerzeichen testest,
auch Newline dazunehmen: " " --> "[ \n]"


Und wenn ich jetzt eh schon so schön am rumtippen bin, hier im Anhang
auch gleich ein Prototyp ... :-)

Ciao,
  Martin
-- 
Martin Ramsch <m.ramsch_(at)_computer.org> <URL: http://ramsch.home.pages.de/ >
PGP: 0xE8EF4F75, 52 44 5E F3 B0 B1 38 26  E4 EC 80 58 7B 31 3A D7

  Das Gedächtnis ist schon eine fabelhafte Sache.  Es funktioniert
  einwandfrei von dem Moment, in dem ich aufwache, bis zu dem Moment,
  in dem ich aufstehe. -- gefunden bei ThH

--cWoXeonUoKmBZSoM
Content-Type: text/plain; charset=us-ascii
Content-Disposition: attachment; filename="replace.php3"

<TITLE>Test</TITLE>

<PRE><?php

$text = "asdas {xyz} {\propname
Ablage}\proptype30{\staticval ABLAGE_TAG} fdsfs
{\propname Ordner}\proptype30{\staticval sfsdf
sdfsdf} asdased";

$property["ablage"]="XXX";
$property["ordner"]="YYY";

echo "--- Alt: -----------------------------------------\n";
echo "$text\n";

for( reset($property); $key = key($property); next($property) ) {

  $pattern = "(\{\\\\propname[ \n]+)"
           . "(" . QuoteMeta($key) . ")"
           . "(\}\\\\proptype30\{\\\\staticval[ \n]+)"
           . "([^}]+)"
           . "(\})"
           . "(.*)";

  print "pattern: $pattern\n";

  $neu = "";
  while ( eregi($pattern, $text, $regs) ) {
    $replace = $property[$key];
    $neu .= eregi_replace($pattern, "\\1\\2\\3$replace\\5", $text);
    $text = $regs[6]; /* Rest durchsuchen */
  }
  $text = $neu . $text;
}

echo "--- Neu: -----------------------------------------\n";
echo "$text\n";
echo "--------------------------------------------------\n";

echo "/\\* \\(c\\) Ramsch\\\\x \\*/\n";
$BS=chr(92);
echo "/".$BS."* ".$BS."(c".$BS.") Ramsch".$BS.$BS."x ".$BS."*/\n"

?></PRE>

--cWoXeonUoKmBZSoM--


php::bar PHP Wiki   -   Listenarchive