Willkommen auf myCSharp.de! Anmelden | kostenlos registrieren
 | Suche | FAQ

Hauptmenü
myCSharp.de
» Startseite
» Forum
» Suche
» Regeln
» Wie poste ich richtig?

Mitglieder
» Liste / Suche
» Wer ist online?

Ressourcen
» FAQ
» Artikel
» C#-Snippets
» Jobbörse
» Microsoft Docs

Team
» Kontakt
» Cookies
» Spenden
» Datenschutz
» Impressum

  • »
  • Community
  • |
  • Diskussionsforum
RegEx kürzester Match [und die Gefahren von .*?]
rollerfreak2
myCSharp.de - Member

Avatar #avatar-3271.jpg


Dabei seit:
Beiträge: 916

Themenstarter:

RegEx kürzester Match [und die Gefahren von .*?]

beantworten | zitieren | melden

Hallo zusammen, ich habe eine Problem mit einem Regex Pattern. Und zwar will ich sowas

<td id="fett"><a name="1481">03.08.2009</a><br></td>

Daraus soll sowas werden

<td><a>03.08.2009</a><br></td>

Das Problem ist der kürzeste RegEx.

Zum Beispiel: Regex=<td.{0,15}>
Da ist das Problem das er immer den längsten Match nimmt. Das ist in meinem Fall ja aber falsch. Ich möchte also nach einem < suchen, dann beliebig viele Zeichen, jedoch kommt dann ein > soll das Pattern matchen, daher > muss exkludiert werden von den eigentlich beliebigen Zeichen. Ich bekomme den Ausdruck aber leider nicht hin.

Hilfe
Again what learned...
private Nachricht | Beiträge des Benutzers
rollerfreak2
myCSharp.de - Member

Avatar #avatar-3271.jpg


Dabei seit:
Beiträge: 916

Themenstarter:

beantworten | zitieren | melden

Ich glaub ich habs, muss es zwar noch verifizieren aber das müsste funzen.

<[^<]*>

Problem ist das gierige und genügsame Verhalten. Kann das eventuell noch jemand bestätigen. Habs kurz mit dem RegexLab getestet, und scheint zu funzen.
Again what learned...
private Nachricht | Beiträge des Benutzers
dN!3L
myCSharp.de - Experte

Avatar #avatar-2985.png


Dabei seit:
Beiträge: 2.891

beantworten | zitieren | melden

Hallo rollerfreak2,

EDIT: Ah, wer lesen kann, ist klar im Vorteil. Du willst einfach nur auf einen Tag matchen.
Wie schon bemerkt, ist das Problem das gierige Verhalten. Folgendes reicht schon aus (genügsames Verhalten durch Fragezeichen "einschalten"):
<.*?>

Gruß,
dN!3L
private Nachricht | Beiträge des Benutzers
herbivore
myCSharp.de - Experte

Avatar #avatar-2627.gif


Dabei seit:
Beiträge: 49.486
Herkunft: Berlin

beantworten | zitieren | melden

Hallo dN!3L,

im Allgemeinen ist jedoch eine Negation sicher als das Fragezeichen.

Hier wäre das: <[^>]*>

herbivore
private Nachricht | Beiträge des Benutzers
rollerfreak2
myCSharp.de - Member

Avatar #avatar-3271.jpg


Dabei seit:
Beiträge: 916

Themenstarter:

beantworten | zitieren | melden

Es gehen beide, wobei ich dem mit der negation einfacher zu lesen finde. Das Fragezeichen schaltet das genügsame Verhalten ein, ist aber schwerer zu lesen.

ps.: Hatte mich oben nur vertippt.

<[^<]*> sollte natürlich <[^>]*> sein.

Danke an euch beide.
Again what learned...
private Nachricht | Beiträge des Benutzers
dN!3L
myCSharp.de - Experte

Avatar #avatar-2985.png


Dabei seit:
Beiträge: 2.891

beantworten | zitieren | melden

Hallo herbivore,
Zitat von herbivore
im Allgemeinen ist jedoch eine Negation sicher als das Fragezeichen.
Hm, warum? Hast du mal ein Beispiel? Bzw. was verstehst du unter "Sicherheit"?

Btw.:
  • <[^<]*> matched:
    <td <id="fett"><a name="1481">
  • <.*?> und <[^>]*> matchen:
    <td <id="fett"><a name="1481">

Gruß,
dN!3L
private Nachricht | Beiträge des Benutzers
herbivore
myCSharp.de - Experte

Avatar #avatar-2627.gif


Dabei seit:
Beiträge: 49.486
Herkunft: Berlin

beantworten | zitieren | melden

Hallo dN!3L,
Zitat
Hast du mal ein Beispiel?
nimm an, du suchst alle Tags, die mit /> abgeschlossen sind. Wenn man dafür das Fragezeichen benutzt, also <.*?/> dann passt das fälschlich auch auf <b>Wichtig</b><br />, matcht also über mehrere Tags hinweg und nicht nur auf <br />, wie das beabsichtigt und bei <[^>]*/> auch der Fall wäre.

Das Fragezeichen sorgt also inbesondere nicht dafür, dass ein Match später beginnt, damit er (noch) kürzer wird. Auch bei Fragezeichen beginnt der Match immer - wie bei Regex üblich - so weit links wie möglich.

Oder anders gesagt, das Fragezeichen macht den Match nicht automatisch so kurz, wie man das erwartet oder sich das wünscht. Man kann da leicht reinfallen.
Zitat
Btw.:
Mal abgesehen davon, dass <[^<]*> ja nicht Absicht, sondern ein Tippfehler war, ist <td <id="fett"> kein syntaktisch korrektes Html. Insofern finde ich es korrekt, dass das Tag nicht richtig erkannt wird. Außerdem kann man diesen Fall durch <[^<>]*> leicht in den Griff bekommen, indem man sowohl schließende als auch öffnende spitze Klammern ausschließt.

herbivore

PS: Wenn man nicht nur ein einzelnes Zeichen ausschließen will (im Beispiel die spitze Klammer zu), sondern eine ganze Zeichenfolge, dann muss man zu negativen Lookaheads greifen.

Mit ((?!hallo).)* findet man einen beliebigen Text, aber nur solange bis das Wort hallo auftaucht. Mit <ul>((?!</?ul>).)*</ul> findet man die zusammengehörigen Tags der (innersten) Bullet-Liste.

Suchhilfe: 1000 Worte, Regex, gierig, Gefahr, gefährlich
private Nachricht | Beiträge des Benutzers
dN!3L
myCSharp.de - Experte

Avatar #avatar-2985.png


Dabei seit:
Beiträge: 2.891

beantworten | zitieren | melden

Hallo herbivore,
Zitat von herbivore
Oder anders gesagt, das Fragezeichen macht den Match nicht automatisch so kurz, wie man das erwartet oder sich das wünscht. Man kann da leicht reinfallen.
Ah OK, einleuchtend. Danke für das Beispiel. =)

Beste Grüße,
dN!3L
private Nachricht | Beiträge des Benutzers