IT-Academy Logo
Sign Up Login Help
Home - Programmieren - Perl - Regular Expressions



Regular Expressions

Einfache Regular Expressions unter Perl werden erklärt...


Autor: Franz Schaefer (mond)
Datum: 25-02-2002, 13:44:59
Referenzen: man perlre
man perlop
Schwierigkeit: Anfänger
Ansichten: 4299x
Rating: 7 (1x bewertet)

Hinweis:

Für den hier dargestellte Inhalt ist nicht der Betreiber der Plattform, sondern der jeweilige Autor verantwortlich.
Falls Sie Missbrauch vermuten, bitten wir Sie, uns unter missbrauch@it-academy.cc zu kontaktieren.

[Druckansicht] [Als E-Mail senden] [Kommentar verfassen]



Übersicht

regular expressions kennen wir schon von grep. die in perl eingebauten
sind noch etwas leistungsfaehiger als die von grep. regular expressions
benutzen wir in perl vorallem auf 2 arten:

s/x/u/ ;

der s/suchmuster/ersetzmuster/ ersetzte das suchmuster durch das
ersetzmuster. im obigen fall macht es einem ein x fuer ein u vor.
allerdings nur eines. will man dass alle x im string durch ein u ersetzte
werden macht man ein g dahinter (fuer global) dahinter:

s/x/u/g ;

der string den der s/// operator ersetzt ist $_. will man auf einem
anderen string arbeiten so gibt man (wie schon bei tr/// gelernt) das mit
dem =~ an:

$text = "felerteufel";

$text =~ s/feler/fehler/ ;

im suchmuster kann man jetzt aehnlich wie bei grep regular expressions
verwenden:

$name=~ s/^[0-9]+/bla/ ;

obiges ersetzt eine ziffernfolge am anfang eines wortes (das ^ zeichen
matched wie auch bei grep auf den anfang der zeichenkette, der ausdruck
[0-9] matched auf eine ziffer (koennte man auch als \d schreiben) und das
+ besagt das ganze mindestens einmal oder oefter vorkommen muss. der
ausdruck matched also auf alle ziffern am anfang einer zeichenkette und
ersettz sie durch das wort "bla".

neben dem s/// operator gibt es noch den m// operator oder einfach nur //
geschrieben. der macht keine ersetzungen sondern prueft nur ob ein string
matched oder nicht.. z.b:


#!/usr/bin/perl -w

while() {
if ( /([0-9\.]+)/ ) {
print "ich habe eine zahl $1 gefunden\n";
}
}

obige schleife liest von STDIN das // durchsucht den string $_ ob dort
eine ziffernfolge (eventuell mit punkt ) ist. wenn ja wird ein print
aufgerufen. in der variablen $1 ist nach der match operation der string
der im ersten () gefunden wurde.

if (/^geburtsdatum: (\d\d\d\d)\-(\d\d)\-(\d\d)/i ) {
$jahr = $1;
$monat = $2;
$tag = $3;
}

obige zeile wuerde also auf zeilen matchen die mit "geburtstdatum: "
beginnen, an den richtigen stellen die \- haben und die teile aus den 3
klammern in variablen $1 $2 und $3 speichern. das i am ende des
suchmusters sagt dass gross und kleinschreibung ignoriert werden sollen.

andere wichtige solcher "modifier" fuer m// und s/// operationen:

i ... case insensitiv. gross/kleinschreibung ignorieren.

e ... der rechte teil eines s/// ausdrucks wird als perl expresson
ausgewertet.

g ... global. alle vorkommnisse des suchstrings einer s/// operation
werden ersettz.

s/(bla|bli|blo)+/alles blabla/g;

wuerde alle vorkomnisse von der ketten bla bli blo oder wenn diese
hintereinander oefter vorkommen durch "alles blabla" ersetzen. also z.b
auch die zeichenkette: blibliblobla. das | trennt gleichwertige
alternativen, die () gruppieren dies und das + sagt dann das beliebig
viele aber mindestens eins davon vorkommen musst damit das suchmuster
passt.

nochmal zur wiederhohlung die bedeutung der zeichen in der regular
expression:

\ zum "escapen" des nachfolgenden zeichen um ihm die
sonderbedeutung zu nehmen.
^ matched auf ein zeilenanfang
. jedes zeichen
$ matched zeilenende
| zum trennen von alternativen
() zum gruppieren
[] zum aufzaehlen von zeichen

dann haben wir die zeichen die festlegen wie oft ein zeichen oder ein
ausdruck vorkommen muss:

* 0 oder mehrmals
+ mindestens 1 mal
? einmal oder 0 male
{n} genau n mal
{n,} mindestens n mal oder mehr
{n,m} mindestens n mal aber maximal m mal.

damit man nicht immer lange [0-9a-z] und aehnliches ausdruecke schreiben
muss gibt es folgende abkuerzungen:


\w "wortzeichen" (alphanumerisch und _)
\W kein wortzeichen
\s whitespace (zwischenraum, tab ..)
\S kein whitespace
\d eine ziffer (digti)
\D keine ziffer

praktisch sind auch.

\b eine wortgrenze (also ein whitspace oder ueberhaupt stringanfang)
\B keine wortgrenze

zum abschluss ein interessantes script:

#!/usr/bin/perl -w

while() {
chomp;
while ( s/\b([a-z]{3,})\b(.*)$/$2/i ) {
print "gefunden $1\n";
}
}

obiges script sucht woerter die nur aus (mindestens 3) buchstaben
bestehen: \b([a-z]{3,})\b

das gefunden wort (erste klammer) ist danach in $1 verfuegbar. der string
$_ wird durch $2 ersetzt (also den rest der zeile). beim naechsten
durchlauf der while schleife wird jetzt die suche auf den verbleibenden
teil in $_ angewendet.... und so weiter.

die schleife gibt also nacheinander alle woerter mit 3 buchstaben aus.

und noch ein kleiner hinweis: man kann statt des / trennzeichens auch
ander zeichen benutzen.

s!x!u!g;

oder

s=x=u=g;

wuerde also ebenfalls ein x durch ein u ersetzten.. sollte man aber nicht
verwenden ausser man hat ein suchmuster mit vielen / drinnen die man sonst
alle mit \ escapen muesste... z.b.:

s!/usr/bin/perl/!/usr/local/bin/perl!g

wuerde alle vorkommnisse des strings /usr/bin/perl durch
/usr/local/bin/perl ersetzten.

EXERCISES:

* schreibe ein script das in allen texten grosse anfangsbuchstaben eines
wortes durch kleine ersetzt aber nur in woerter. einzelen buchstaben[B
oder woerter die GANZ grossgeschrieben sind sollen bleiben wie sie
waren.

* schreibe ein script das die ausgabezeilen eines programms wie ps oder
who oder w oder finger oder last mit einer regular expression in
einzelne felder zerteilt.

* schreibe ein script das ein textfile nach preisangaben in EUR (also nach
ausdruecken wie EUR 34.80 EUR oder EUR 234) durchsucht und den EUR
preis hinter die zahl in schilling schreibt:

also etwa so: aus d
der preis ist EUR 100
wird:
der preis ist EUR 100 (ATS 1376.03).

(beachtet es koennen mehr als ein EUR preis pro zeile vorkommen).
hilfestellung: um eine flieskommazahl auf 2 stellen gerundet auszugeben
verwendet man z.b.: sprintf("%0.2f",$preisinats)



_______________________________________________
CD ist ein service von SILVER SERVER
der inhalt unterliegt der GFDL
_______________________________________________



dreamer
Expert
Beitrag vom:
02-11-2004, 12:18:33

Guter Artikel

Der Artikel ist gut geschrieben (vor allem die Übungsaufgaben am Ende sind eine tolle Idee), allerdings muss ich zwei Dinge bemängeln:

1) leider wurde der Text nicht ausreichend formatiert, wodurch der Text etwas mühsam zu lesen ist.

2) es gibt für die Übungen am Ende keine Beispiellösungen.

-----------------------------------------------------


[back to top]



Userdaten
User nicht eingeloggt

Gesamtranking
Werbung
Datenbankstand
Autoren:04503
Artikel:00815
Glossar:04116
News:13565
Userbeiträge:16551
Queueeinträge:06238
News Umfrage
Ihre Anforderungen an ein Online-Zeiterfassungs-Produkt?
Mobile Nutzung möglich (Ipone, Android)
Externe API Schnittstelle/Plugins dritter
Zeiterfassung meiner Mitarbeiter
Exportieren in CSV/XLS
Siehe Kommentar



[Results] | [Archiv] Votes: 1137
Comments: 0