Über Treffer iterieren

Photon

Rear Admiral Pro
🎅Rätsel-Elite ’24
Registriert
Apr. 2006
Beiträge
5.553
Hallo Community,

ich bin eine totale Niete in Regular Expressions und bräuchte hier kurz Hilfe: Ich möchte eine Textdatei einlesen und dann Treffer nach dem Schema

Code:
\begin{frame}{TITEL}

finden (TITEL ist variabel, der Rest fix) und ersetzen mit

Code:
\begin{frame}
\stitle{TITEL}{id_N}

wobei N die Nummer des Treffers ist. Wenn es hilft, die Treffer sind vollständige Zeilen, sie sind also allein in ihrer Zeilen, allerdings gibt es natürlich viele weitere Zeilen mit anderem Inhalt, die keinen Treffer beinhalten.

Ich beichte gleich, dass ich zu diesem konkreten Problem selbst noch nicht recherchiert habe; weiß aber aus früherer Erfahrung, dass mich das einige Stunden kosten dürfte, es also schneller wäre das Ganze von Hand zu machen (~200 Treffer). Aber falls jemand da ein Stück fitter ist als ich und die Lösung aus dem Ärmel schütten kann, wäre es mir eine große Hilfe und Zeitersparnis. Die verwendete Sprache spielt übrigens keine Rolle.

Vielen Dank, falls jemand sich die Mühe macht da ein kleines Skript zu basteln!
Photon
 
Bin gerade am Handy aber schau doch Mal ob das Stichwort HTML Tag regexp dir weiter hilft, das ist von der Struktur her ähnlich.
mMn lohnt es sich sowas mit regexp zu machen auch wenn es länger dauert. Mittlerweile geht es durch solcherlei halbwegs gut bei mir.
Jedenfalls willst du TITLE in eine Group packen mit ( ) und die kannst du dann mit \1 referenzieren.
 
Danke für den Input! Klar, dass man da regexp braucht, versteh ich schon, nur bin ich da leider noch nicht so bewandert und möchte nicht zu viel Zeit reinstecken. Möchte auch nicht, dass jemand anders viel Zeit reinsteckt, hatte bloß die Hoffnung, dass vielleicht jemand über den Thread stolpert, für den das kein Aufwand ist. Das Skript dürfte nur wenige Zeilen lang werden, aber die Recherche dazu, wenn man bei nahezu Null startet, dürfte lange dauern...
 
Python:
import re

RE_PATTERN = r'\\begin{frame}{(\w+)}'
REPL_STR = r"""\begin{frame}
\stitle{%s}{id_%s}"""

REPL_COUNT = 0


def repl(matchobj):
    global REPL_COUNT
    inner_text = matchobj.group(1)
    ret = REPL_STR % (inner_text, REPL_COUNT)
    REPL_COUNT = REPL_COUNT + 1
    return ret


try:
    with open('input.tex', 'r') as f:
        t = f.read()
except OSError:
    print('file not found')
    exit(1)

t = re.sub(RE_PATTERN, repl, t)

try:
    with open('input_replaced.tex', 'x') as f:
        f.write(t)
except OSError:
    print('create new file failed')
    exit(1)

test input:
\begin{frame}{TITLE_1}abcdefghijkl
abcdefghijkl
\begin{frame}{TITLE_2}

\begin{frame}{TITLE_3}
abcdefghijkl
abcdefghijkl



\begin{frame}{TITLE_4}

test output:
\begin{frame}
\stitle{TITLE_1}{0}abcdefghijkl
abcdefghijkl
\begin{frame}
\stitle{TITLE_2}{1}

\begin{frame}
\stitle{TITLE_3}{2}
abcdefghijkl
abcdefghijkl



\begin{frame}
\stitle{TITLE_4}{3}

edit: zeile 5 ausgebessert damit mit "id_0", "id_1", ... statt nur mit der Ziffer ersetzt wird
 
Zuletzt bearbeitet:
Das sieht super aus, vielen Dank! Werde das gleich über die betreffenden Dateien drüberjagen und berichten!
Ergänzung ()

Nachtrag: Klappt fast gut, nur wenn TITLE Leerzeichen enthält, dann wird der Treffer nicht gefunden. Gibt es vielleicht irgendwelche schwarze Magie, die alle Sonderzeichen (außer eben dem schließenden }) oder zumindest Leerzeichen in TITLE erlaubt? Danke!
 
Zuletzt bearbeitet:
Photon schrieb:
Das sieht super aus, vielen Dank! Werde das gleich über die betreffenden Dateien drüberjagen und berichten!
Ergänzung ()

Nachtrag: Klappt fast gut, nur wenn TITLE Leerzeichen enthält, dann wird der Treffer nicht gefunden. Gibt es vielleicht irgendwelche schwarze Magie, die alle Sonderzeichen (außer eben dem schließenden }) oder zumindest Leerzeichen in TITLE erlaubt? Danke!

{([\w\s]+)} statt {(\w+)}, das matcht dann groß/kleinbuchstaben, underscore und whitespace
 
Üff, jetzt merke ich, es scheitert auch an Bindestrichen und ggf. runden Klammern (im entsprechenden TITLE ist beides enthalten)... Eine schnelle Google-Suche sagt, man soll in die erlaubten Zeichen noch ein escaptes Minus aufnehmen, also nach meinem Verständnis {([\w\s\-]+)} aber irgendwie will das nicht klappen. :) Was mache ich denn falsch?
 
Python:
RE_PATTERN = r'\\begin{frame}{([\w\s\-\"\§\#\$\%\&\\\'\(\)\*\+\,\-\.\/\:\;\<\=\>\?\@\[\]\^\_\`\|\~]+)}'

probier das mal, geht sicher eleganter aber bin nicht so der regex guru ;)
 

Ähnliche Themen

Zurück
Oben