Reguläre Ausdrücke: Text ausschneiden
Reguläre Ausdrücke: Text ausschneiden
am 23.04.2006 10:02:35 von Heiko Rompel
Moin,
ich habe mal wieder Probleme mit Regulären Ausdrücken.
Ich habe folgendes:
@file mit solchen Zeilen:
Sonntag, 16. April, 2006 um 13:05|Heiko Rompel|
src="ppviewer2003.exe" alt="" />|none|
|192.168.0.240|
und möchte nur den Teil haben der zwischen
scr=" und " alt= steht.
Wenn ich das wie folgt mache, dann bleibt $f leer:
foreach $f (@file){
$f = /
/;
print ("###".$f."\n");
};
Was mache ich falsch?
MfG
Heiko
Re: Reguläre Ausdrücke: Text ausschneiden
am 23.04.2006 10:31:15 von df4or
Heiko Rompel wrote:
> Ich habe folgendes:
> @file mit solchen Zeilen:
> Sonntag, 16. April, 2006 um 13:05|Heiko Rompel|
> src="ppviewer2003.exe" alt="" />|none|
|192.168.0.240|
>
> und möchte nur den Teil haben der zwischen
> scr=" und " alt= steht.
>
> Wenn ich das wie folgt mache, dann bleibt $f leer:
>
> foreach $f (@file){
> $f = /
/;
> print ("###".$f."\n");
> };
>
> Was mache ich falsch?
Verschiedenes.
> $f = /
/;
1.)
Was erwatest Du, was $f nach Ausführung dieser Zeile beeinhalten sollte?
Doch sicher nicht den gefundenen Ausdruck. m// liefert True oder False
zurück.
Richtig wäre
$f =~ /
/;
Das worauf .+ gematcht hat steht dann in $1.
2.)
Du vergisst das '.' normalerweise kein Newline matcht. Versuchs mit
$f =~ /
/s;
^
oder nimm vor dem Vergleich die Newlines mit $f =~ s/\n//; raus.
Das Resultat findet Du in $1.
3.)
Nicht falsch aber verbesserungswürdig:
Anstatt
> print ("###".$f."\n");
schreib doch gleich
print ("###$f\n");
Desweiteren nehme ich an das Du unvollständiges ein Codesnippet gepostet
hast.
foreach $f (@file)
liefert Dir in $f den Filenamen, nicht den Inhalt. Und ich nehme weiters an
das Deine Files nicht
heissen.
Gruß,
Ekki
Re: Reguläre Ausdrücke: Text ausschneiden
am 23.04.2006 10:39:29 von Frank Wiegand
Heiko Rompel schrieb:
> foreach $f (@file){
foreach my $f (@file) {
> $f = /
/;
^ ^ ^
1. Du willst keine Zuweisung, sondern Pattern matching.
2. .+ ist greedy
3. das '>' ist dein Denkfehler.
> print ("###".$f."\n");
perl kennt interpolierte Strings, und bei Builtins sollte man die
Klammern weglassen.
> };
Semikolon ist hier unnötig.
Also:
use warnings;
use strict;
foreach my $f (@file) {
$f =~ /
print "###$1\n" if $1;
}
Hättest du `use warnings' benutzt, wärst du von alleine ein Stück weiter
gekommen.
Frank
Re: Reguläre Ausdrücke: Text ausschneiden
am 23.04.2006 13:38:07 von Heiko Rompel
Hallo,
> Verschiedenes.
Das ist nicht gut.
>> $f = /
/;
>
> 1.)
> Was erwatest Du, was $f nach Ausführung dieser Zeile beeinhalten sollte?
> Doch sicher nicht den gefundenen Ausdruck. m// liefert True oder False
> zurück.
Ich hatte sogar vorher die '~' drin, aber da der Rest fehlerhaft war,
nahm ich die wieder raus.
> Richtig wäre
> $f =~ /
/;
> Das worauf .+ gematcht hat steht dann in $1.
Das mit dem '$1' stand in keinem der Beispiel die ich gefunden hatte.
> Du vergisst das '.' normalerweise kein Newline matcht.
Was ich nicht wußte, kann ich auch icht vergessen. :-)
> Versuchs mit $f =~ /
/s;
Okay, habe das 's' übernommen.
> oder nimm vor dem Vergleich die Newlines mit $f =~ s/\n//; raus.
Welche Variante ist denn die bessere?
> Das Resultat findet Du in $1.
Oh man, dieser $1 schon wieder :-)
> schreib doch gleich
> print ("###$f\n");
Okay, die Pinkte waren nur ein weiterer Versuch.
> Desweiteren nehme ich an das Du unvollständiges ein Codesnippet gepostet
> hast.
> foreach $f (@file)
> liefert Dir in $f den Filenamen, nicht den Inhalt.
Nein, wie im OP eine Textzeile in der der Filename im Text steht. (Zeile 7
im OP)
> Und ich nehme weiters an
> das Deine Files nicht
heissen.
Richtig. Der Filename steht hinter dem 'scr=' .
Deine Beispielzeile $f =~ /
/s;
funktioniert aber nicht. Erst wenn ich das letzte '>' entferne, klappt es.
Trotzdem Danke.
MfG
Heiko
Re: Reguläre Ausdrücke: Text ausschneiden
am 23.04.2006 13:49:19 von Heiko Rompel
Hallo,
"Frank Wiegand" schrieb:
> foreach my $f (@file) {
Die Variablen werden im Script weiter oben schon definiert,
also kann ich das 'my' hier weg lassen.
>> $f = /
/;
> ^ ^ ^
> 1. Du willst keine Zuweisung, sondern Pattern matching.
Ja.
> 2. .+ ist greedy
greddy? - Keine Übersetzung davopn gefunden.
> 3. das '>' ist dein Denkfehler.
Jupp, danke.
>
>> print ("###".$f."\n");
> perl kennt interpolierte Strings,
Okay, die Punkte sind raus.
> und bei Builtins sollte man die Klammern weglassen.
Tja, das scheint auch wieder so eine Glaubensfrage zu sein.
Zitat aus "Mit Perl programmieren lernen" 1.Ausgabe Seite 54 Abs. 1:
>>"Die notation ohne Klammern haben wir zuvor schon für 'return' verwendet.
Sie ist für alle vordefinierten Funktionen erlaubt, aber nicht unbedingt zu
empfehlen."<<
>> };
> Semikolon ist hier unnötig.
Unnötig oder unzulässig?
> foreach my $f (@file) {
> $f =~ /
> print "###$1\n" if $1;
> }
Jupp, das läuft.
> Hättest du `use warnings' benutzt, wärst du von alleine ein Stück weiter
> gekommen.
Ich habe sogar das drin:
use warnings;
use diagnostics;
use strict;
Wenn man aber nicht versteht, was ein die englische Fehlermeldung
sagen will ....
Danke, für Deine Hilfe.
MfG
Heiko
Re: Reguläre Ausdrücke: Text ausschneiden
am 23.04.2006 14:14:02 von Frank Wiegand
Heiko Rompel schrieb:
>> foreach my $f (@file) {
> Die Variablen werden im Script weiter oben schon definiert,
Wozu? Sind wir hier bei C?
Du durchläufst das Array @file, bei jedem Durchlauf wird der aktuelle
Wert auf $f gealiast. Vor und nach dem Durchlauf ist der Wert von $f
nicht sinnvoll zu verwenden.
>> 2. .+ ist greedy
> greddy? - Keine Übersetzung davopn gefunden.
Es heißt "greedy", wie "gierig". .+ frißt also soviel, wie es kann, und
nicht soviel, wie es muss. Siehe dict.leo.org für Übersetzungen.
>>> };
>> Semikolon ist hier unnötig.
> Unnötig oder unzulässig?
Unnötig. Das Ende von Blöcken ist eindeutig, deswegen muss man das nicht
noch extra anzeigen.
> Wenn man aber nicht versteht, was ein die englische Fehlermeldung
> sagen will ....
Dann lerne Englisch. Und wenn es immer noch unklar ist, dann schreib die
Fehlermeldung in deine Frage. Sonst weiß ja keiner, was dein Problem ist.
In "Programmieren mit Perl" (ISBN 3-89721-144-0) stehen deutsche
Erlärungen der Fehlermeldungen (Stand: Perl 5.6) drin.
Frank
Re: Reguläre Ausdrücke: Text ausschneiden
am 24.04.2006 14:53:50 von Ferry Bolhar
Heiko Rompel:
> > 2. .+ ist greedy
>
> greddy? - Keine Übersetzung davopn gefunden.
Weil du es falsch geschrieben hast ("edd" statt "eed"). "Greedy" steht für
"gierig" und meint in diesem Fall, dass
(soferne es nicht anders angegeben ist) in regulären Ausdrücken Quantifier
wie '+' oder '*' immer _soviel wie
möglich_ matchen, dh. beim Matchen gierig sind. Das kann manchmal zu
unerwarteten Ergebnissen führen.
Das Gegenteil ist übrigens "lazy" (faul), dh., solche Quantifier matchen nur
soviel, wie sie müssen. In Perl
stellt man dazu den "greedy" Quantifiern ein "?" nach (dh,. '+?' oder '*?').
>> und bei Builtins sollte man die Klammern weglassen.
>
> Tja, das scheint auch wieder so eine Glaubensfrage zu sein.
>
> Zitat aus "Mit Perl programmieren lernen" 1.Ausgabe Seite 54 Abs. 1:
> >>"Die notation ohne Klammern haben wir zuvor schon für 'return'
verwendet.
> Sie ist für alle vordefinierten Funktionen erlaubt, aber nicht unbedingt
zu
> empfehlen."
Dein Code wird für andere lesbarer (und man sollte nie ausschließen, dass
die eigene Programmiererei
auch mal von anderen gelesen werden muss!), wenn du bestimmte Standards
einhältst. Einer davon ist,
dass man bei Built-in Funktionen, die nicht also solche verwendet werden
(und das ist hier der Fall, weil
du den Rückgabewert, den dir 'print' liefern würde, verwirfst), die Klammern
wegläßt, dh., eine "befehls-
ähnliche" Syntax verwendet.
Gerade in einer Sprache wie Perl, die syntaxmäßig sehr viele Freiheiten
läßt, sollte man sich an solche
Standards halten. Bei uns im Haus gibt es zB. ebenfalls solche Standards,
die aus dem - IMHO
übrigens sehr empfehlenswerten - Buch "Perl Best Practices" (O'Reilly 2005,
ISBN 0-596-00173-8)
abgeleitet wurden (einige Standards gab es schon vorher; sie wurden dadurch
nur verfeinert).
> >> };
> > Semikolon ist hier unnötig.
>
> Unnötig oder unzulässig?
Ersteres. Ein Block wird durch "{" und "}" begrenzt, daher ist hier ein
Semikolon, dass in Perl als
Befehlsbegrenzer verwendet wird, überflüssig.
> Wenn man aber nicht versteht, was ein die englische Fehlermeldung sagen
will ....
Dann solltest du dir eine Erklärung der Fehlermeldungen besorgen (gibt es
zB. im "Kamelbuch"
auch auf Deutsch!) oder soweit Englisch lernen, dass du die Meldungen
verstehen kannst.
LG, Ferry
--
Ing. Ferry Bolhar
Municipality of Vienna, Department 14
A-1010 Vienna / AUSTRIA
E-mail: bol@adv.magwien.gv.at