preg-match für einzelne wörter im Satz

Einklappen
X
 
  • Filter
  • Zeit
  • Anzeigen
Alles löschen
neue Beiträge

  • preg-match für einzelne wörter im Satz

    Hallo, ich benutze dies Abfrage um bei Wörtern die nur einen Vokal haben vor diesen einen Slash zu setzen:

    if (!mb_strstr($text,"/") AND preg_match_all("![аеиоуяюёэы]!u",$text,$dummy)==1) $text = preg_replace("!(.*)([аеиоуяюёэйы])!u","$1/$2",$text);
    Das funktioniert gut bei einzelnen Wörtern, aber wenn ich nun einen Satz mit mehreren Wörtern habe, dann kommen ja insgesamt mehrere Vokale vor auch wenn es wörter mit nur einem gibt. Gibt es nun eine möglichkeit, das bei dem regulären ausdruck zu berücksichtigen, oder muss ich den satz erst in wörter zerstückeln?

    Gruß

  • #2
    Man kann das Vorkommen von word boundaries verlagen.
    http://www.php.net/manual/en/regexp.....backslash.php

    Allerdings ist die Definition, was eine Wortgrenze darstellt, von der im System eingestellten locale abhängig.
    I don't believe in rebirth. Actually, I never did in my whole lives.

    Kommentar


    • #3
      danke für die Antwort, aber da blick ich gar nicht durch ?!

      Kommentar


      • #4
        Hier mal ein Lösungsansatz. Die beiden Zeichenklassen hab ich aus reiner Bequemlichkeit nur mit ASCII-Buchstaben getestet. Du darfst sie aber gerne mit den von dir benötigten Vokalen und Konsonanten füllen. Es müssen aber alle Buchstaben erfasst werden, sonst funktioniert das Ganze nicht. Groß- und Kleinbuchstaben müssen jeweils extra aufgelistet werden. Der Modifikator /i könnte hier Arbeit abnehmen, funktioniert aber leider nicht mit UTF-8 und auch nicht mit Codepages (das Locale-Geraffel).

        PHP-Code:
        $pcre '/
            (?(DEFINE)(?<vowel>[AEIOUaeiou]))
            (?(DEFINE)(?<nonvowel>[BCDFGHJ-NP-TV-Zbcdfghj-np-tv-z]))

            (?<=\P{L}|\A)(?=(?&nonvowel)*(?&vowel)(?&nonvowel)*(?:\P{L}|\z))
        /xU'
        ;

        preg_match_all($pcre$kopna$goli);
        var_dump($goli);

        $replaced preg_replace($pcre'-$0'$kopna);
        var_dump($replaced); 
        Der RegEx ist prinzipiell UTF-8-tauglich. Du musst aber beim Auffüllen der Zeichenklassen darauf achten, dass dein Editor auch UTF-8 unterstützt. Wenn er das nicht tut, solltest du die Zeichen als \x{NNN}-Sequenzen eingeben.

        Zitat von Jeremy Beitrag anzeigen
        danke für die Antwort, aber da blick ich gar nicht durch ?!
        "Word-boundaries sind locale-abhängig", heißt:

        1.) "Wortgrenzen" suchen nach Buchstaben-Nichtbuchstaben-Kombinationen. Ein "Wort" in PCRE besteht immer aus Buchstaben. Ein Nicht-Wort-Bereich besteht aus allen anderen Zeichen (aber nicht aus Buchstaben).

        2.) Was ein Buchstabe ist, wird in PHP's PCRE durch die setlocale()-Einstellung mitbestimmt. Die Zeichenklassen [A-Za-z] gehören zum ASCII-Bereich und sind immer Buchstaben. Deutsche Umlaute und Buchstaben mit Akzent stehen auf Zeichenpositionen oberhalb des ASCII-Bereichs. Abhängig von der verwendeten Codepage kann die gleiche Zeichenposition einen Buchstaben oder einen Nicht-Buchstaben darstellen.
        Zuletzt geändert von fireweasel; 21.06.2010, 10:29.
        Klingon function calls do not have “parameters”‒they have “arguments”‒and they always win them!

        Kommentar


        • #5
          hi,

          vielen dank für den code,klappt schonmal ziemlich gut, dass er die richtigen wörter rausfindet. Allerdings packt er beim replace das Zeichen genau vor das wort und nicht vor den entsprechenden vokal im Netz, wie könnte man das noch ändern?

          Gruß

          Kommentar


          • #6
            Zitat von Jeremy Beitrag anzeigen
            hi,

            vielen dank für den code,klappt schonmal ziemlich gut, dass er die richtigen wörter rausfindet. Allerdings packt er beim replace das Zeichen genau vor das wort und nicht vor den entsprechenden vokal im Netz, wie könnte man das noch ändern?
            This behaviour is intentional. ... oder so ähnlich. Ich hatte deine Problemstellung so verstanden. Sonst hätte ich den Regex nicht in eine Assertion gesteckt.

            So müsste das jetzt besser passen:
            PHP-Code:
            $pcre '/
                (?(DEFINE)(?<vowel>[AEIOUaeiou]))
                (?(DEFINE)(?<nonvowels>[BCDFGHJ-NP-TV-Zbcdfghj-np-tv-z]*))


                (?<=\P{L}|\A)(?&nonvowels)(?&vowel)(?&nonvowel)(?=\P{L}|\z)
            /xU'
            ;

            preg_match_all($pcre$kopna$goli);
            var_dump($goli);

            $replaced preg_replace($pcre'$1-$2$3'$kopna);
            var_dump($replaced); 
            Man beachte die kleine (aber wichtige) Änderung im "nonvowel"-Bereich.
            Zuletzt geändert von fireweasel; 21.06.2010, 10:29.
            Klingon function calls do not have “parameters”‒they have “arguments”‒and they always win them!

            Kommentar


            • #7
              hallo, klappt leider auch nicht

              Da ist noch ein kleiner rechtschreibfehler (nonvowel statt nonvowels), aber auch dann ersetzt er nun leider gar nichts mehr bei einem normalen wort,hat man allerdings nur einen Vokal ohne Konsonant wird der einfach komplett gelöscht..

              Kommentar


              • #8
                Zitat von Jeremy Beitrag anzeigen
                hallo, klappt leider auch nicht

                Da ist noch ein kleiner rechtschreibfehler (nonvowel statt nonvowels), aber auch dann ersetzt er nun leider gar nichts mehr bei einem normalen wort,hat man allerdings nur einen Vokal ohne Konsonant wird der einfach komplett gelöscht..
                Huch, werd ich hier nach Stunden bezahlt?
                Selbst ist der debuggende Scriptbastler, oder so ähnlich ...

                Nimm dir einen "Heuhaufen"-String vor, in dem ein Wort vorkommt, dass vor und nach dem einzigen Konsonant mehrere Vokale hat. Dann wirfst du das preg_match() zum Fraß vor. Lass dir das Treffer-Array anzeigen. Die Index-Nummern der Einträge, die die "Vor"-Konsonanten, den Vokal und die "Danach"-Konsonanten enthalten, sollten die richtigen Nummern sein. Mit diesen ersetzt du die Nummern in meinem ursprünglichen Ersetzen-String.

                Es dürfte sich mit hoher Wahrscheinlichkeit um 3, 4 und 5 handeln (also '$3-$4$5'). Ich hatte vergessen, dass die DEFINE-Subpattern auch mitgezählt werden müssen. Die sind noch etwas neu für mich.

                Das mit den "nonvowels" hatte ich tatsächlich übersehen.
                Klingon function calls do not have “parameters”‒they have “arguments”‒and they always win them!

                Kommentar

                Lädt...
                X