Textblöcke aus Quelldatei filtern und in neue Datei schreiben
Hallo liebe Admins!
Mein Problem ist, das ich nicht weiss wie ich eine .txt Datei so zerfilter oder absuche, dass ich genau den Bereich an Text rausbekomme, den ich gerne haben möchte (also ein von-da-bis-da-Problem).
Hier mein Beispieltext (beispiel.txt):
Ich möchte den Text von Zeile 1-4, 9-12 usw haben, jedoch nicht den von 17-20.
Im Beispiel hier sind immer nur 2 Kommentarzeilen, aber ich habe auch größere Bereiche (die vorher unbekannt sind). Also kann ich auch nicht einfach nach test1() etc. suchen und dann sagen die nächsten 3 Zeilen noch mitnehmen.
Wie könnte man das mit Batch lösen?
Hoffentlich kann mir jemand helfen.
Liebe Grüße
Mein Problem ist, das ich nicht weiss wie ich eine .txt Datei so zerfilter oder absuche, dass ich genau den Bereich an Text rausbekomme, den ich gerne haben möchte (also ein von-da-bis-da-Problem).
Hier mein Beispieltext (beispiel.txt):
//---- test() ------------------//
// 1. kommentarzeile //
// 2. kommentarzeile //
//------------------------------//
proc test()
/****************************************************/
/* BLABLA zu proc test() */
/****************************************************/
//---- test2(parameter1, parameter2) ----//
// 1. kommentarzeile //
// 2. kommentarzeile //
//------------------------------//
proc test2(parameter1, parameter2)
/****************************************************/
/* BLABLA ZU proc test2(parameter1, parameter2) */
/****************************************************/
//--------------------------------//
// zwischendrin steht unwichtiges //
// das will ich nicht haben //
//--------------------------------//
//---- test3() -------------------//
// 1. kommentarzeile //
// 2. kommentarzeile //
//--------------------------------//
proc test3zusatz()
/****************************************************/
/* BLABLA ZU proc test3zusatz() */
/****************************************************/
//____________________
// test4()
//____________________
// 1. kommentarzeile
// 2. kommentarzeile
//____________________
template test4()
Ich möchte den Text von Zeile 1-4, 9-12 usw haben, jedoch nicht den von 17-20.
Im Beispiel hier sind immer nur 2 Kommentarzeilen, aber ich habe auch größere Bereiche (die vorher unbekannt sind). Also kann ich auch nicht einfach nach test1() etc. suchen und dann sagen die nächsten 3 Zeilen noch mitnehmen.
Wie könnte man das mit Batch lösen?
Hoffentlich kann mir jemand helfen.
Liebe Grüße
Bitte markiere auch die Kommentare, die zur Lösung des Beitrags beigetragen haben
Content-ID: 147176
Url: https://administrator.de/forum/textbloecke-aus-quelldatei-filtern-und-in-neue-datei-schreiben-147176.html
Ausgedruckt am: 01.05.2025 um 22:05 Uhr
14 Kommentare
Neuester Kommentar
Hallo peter8810!
Unter der Voraussetzung, dass es immer definierte Blöcke mit Beginn %Von% (inklusive) und Ende %Bis% (exklusive) - wie in den Zeilen 4 und 5 festgelegt - gibt und keine Sonderzeichen "<|>&" enthalten sind, versuch es mal so:
In den Zeilen 2 und 3 können natürlich auch komplette Dateipfade verwendet werden. Falls auch die Zeile mit der %Bis%-Markierung noch geschrieben werden soll, die Zeilen 14 und 15 vertauschen.
Die verwendete Technik: Abhängig vom Zustand des "Schalters" %Schreiben% (gesetzt oder leer = "
Nach dem gleichen Prinzip, aber ohne Unterprogramm sähe das dann so aus:
[Edit] Mit "
Grüße
bastla
Unter der Voraussetzung, dass es immer definierte Blöcke mit Beginn %Von% (inklusive) und Ende %Bis% (exklusive) - wie in den Zeilen 4 und 5 festgelegt - gibt und keine Sonderzeichen "<|>&" enthalten sind, versuch es mal so:
@echo off & setlocal
set "Ein=Beispiel.txt"
set "Aus=Gefiltert.txt"
set "Von=//---- "
set "Bis=proc"
del "%Aus%" 2>nul
set "Schreiben="
for /f "tokens=1* delims=:" %%i in ('findstr /n "^" "%Ein%"') do call :ProcessLine "%%j"
goto :eof
:ProcessLine
echo\%~1|findstr /b /c:"%Von%">nul && set "Schreiben=True"
echo\%~1|findstr /b /c:"%Bis%">nul && set "Schreiben="
if defined Schreiben >>"%Aus%" echo\%~1
goto :eof
Die verwendete Technik: Abhängig vom Zustand des "Schalters" %Schreiben% (gesetzt oder leer = "
not defined
") wird jede einzelne Zeile in die Zieldatei geschrieben, wobei ab einer Zeile, die mit dem in %Von% festgelegten String beginnt das Schreiben "eingeschaltet" und ab einer mit "%Bis%" beginnenden Zeile das Schreiben wieder "ausgeschaltet" wird.Nach dem gleichen Prinzip, aber ohne Unterprogramm sähe das dann so aus:
@echo off & setlocal
set "Ein=Beispiel.txt"
set "Aus=Gefiltert.txt"
set "Von=//---- "
set "Bis=proc"
del "%Aus%" 2>nul
set "Schreiben="
for /f "tokens=1* delims=:" %%i in ('findstr /n "^" "%Ein%"') do (
echo\%%j|findstr /b /c:"%Von%">nul && set "Schreiben=True"
echo\%%j|findstr /b /c:"%Bis%">nul && set "Schreiben="
if defined Schreiben echo\%%j
)>>"%Aus%"
echo\
" durchgängig für Leerzeilen vorgesorgt [/Edit]Grüße
bastla

Hallo bastla,
ich mag mich täuschen, aber bei deiner Version kommt doch die proc-Zeile nicht mit raus?
Du warst schneller, meine Version sah ähnluch aus.
Gruß
LotPings
Edit: damit ich nicht noch mehr Beulen von Bibers Doku-Keule kriege:
ich mag mich täuschen, aber bei deiner Version kommt doch die proc-Zeile nicht mit raus?
Du warst schneller, meine Version sah ähnluch aus.
:: Peter8810.cmd::::::::::::::::::::::::::::::::::::::::::::::::::::::
:: LotPings administrator.de 2010-07-19
@echo off & Setlocal
Set Inp="Input.txt"
Set Out="output.txt"
If defined Flag Set "Flag="
For /f "usebackq delims=" %%A in (%Inp%) Do Set "Line=%%A" & Call :ProcLine
Goto :eof
:ProcLine
Echo.%Line%| Findstr "^//-*.*(.*).-*//$" >NUL 2>&1 && Set Flag=Ok
If not defined Flag goto :Eof
>>%Out% Echo.%Line%
If /I "%Line:~0,4%" EQU "proc" Set "Flag="
Gruß
LotPings
Edit: damit ich nicht noch mehr Beulen von Bibers Doku-Keule kriege:
- Die For Schleife verarbeitet alle Zeilen und gibt sie an die Sub ProcLine in der Variable Line weiter.
- Die Zeile 10 stellt über eine RegularExpression fest, ob die Startbedingung gegeben ist und setzt die Var Flag
- solange Flag gesetzt ist werden die Zeilen ausgegeben
- wenn die ersten 4 Zeichen "proc" enthalten wird Flag zurückgesetzt.
Hallo LotPings!
Grüße
bastla
ich mag mich täuschen, aber bei deiner Version kommt doch die proc-Zeile nicht mit raus?
Hatte es zunächst so verstanden (und bin mir noch immer nicht ganz sicher), dass sie das auch nicht sollte, und dann nur beiläufig nachgereicht (durch Vertauschen der Zeilen zum Flag-Rücksetzen und Schreiben - in der ersten Version Zeilen 14 und 15 - wird auch die %Bis%-Zeile noch geschrieben) ...Grüße
bastla

Hallo Peter,
vorausgesetzt die Kommentare enthalten keine Sonderzeichen, sollte dies funktionieren
Mein Batch hatte keinen sichtbaren output, sondern schreibt nur in die per Out referenzierte Datei, hab ich geändert mit einer Pause.
Gruß
LotPings
vorausgesetzt die Kommentare enthalten keine Sonderzeichen, sollte dies funktionieren
:: Peter8810.cmd::::::::::::::::::::::::::::::::::::::::::::::::::::::
:: LotPings administrator.de 2010-07-19
@echo off & Setlocal
Set Inp="Input.txt"
Set Out="output.txt"
Type NUL >%Out%
If defined Flag Set "Flag="
For /f "delims=" %%A in (
'Findstr /I "^//.*//$ ^proc" %Inp%'
) Do Set "Line=%%A" & Call :ProcLine
Pause
Goto :eof
:ProcLine
Echo.%Line%| Findstr "^//-*.*(.*).-*//$" >NUL 2>&1 && Set Flag=Ok
If not defined Flag goto :Eof
Echo.%Line%
>>%Out% Echo.%Line%
If /I "%Line:~0,4%" EQU "proc" Set "Flag="
Mein Batch hatte keinen sichtbaren output, sondern schreibt nur in die per Out referenzierte Datei, hab ich geändert mit einer Pause.
Gruß
LotPings

Zitat von @peter8810:
So in etwa nur im großen Stil versteht sich :D Bin noch am googlen und lesen, um es hinzubekommen. Hab da auch Probleme bei
der FOR-Schleife in Batch. Wenn ich Variablen habe, die in der FOR-Schleife stehen, verändern sich diese nicht. Und bei echo
%var% kommt nur raus "ECHO ist ausgeschaltet (off)". Damit das klappt muss ich doch nur am Anfang der Batch zum
"@echo off" das "& setlocal" hinzufügen, oder brauch ich noch mehr, damit sich die Variable
verändert?
So in etwa nur im großen Stil versteht sich :D Bin noch am googlen und lesen, um es hinzubekommen. Hab da auch Probleme bei
der FOR-Schleife in Batch. Wenn ich Variablen habe, die in der FOR-Schleife stehen, verändern sich diese nicht. Und bei echo
%var% kommt nur raus "ECHO ist ausgeschaltet (off)". Damit das klappt muss ich doch nur am Anfang der Batch zum
"@echo off" das "& setlocal" hinzufügen, oder brauch ich noch mehr, damit sich die Variable
verändert?
- Wenn du mit Echo eine leere Variable ausgibst, interpretiert echo das als Aufforderung seinen Status auszugeben,
- Das Variablen in geklammerten Bereichen nicht aktualisiert werden fällt unter das lange Thema "DelayedExpansion" kann man mit
SetLocal EnableDelayedExpansion
und Benutzung von ! statt des % oder einem Pseudo Call mit verdoppelten %-Zeichen oder durch die Benutzung von Subs umgehen ( wie in meinem Batch)
P.S.: Bei deinem ersten Code ist überhaupt nichts passiert. Damit meinte ich auch das nichtmal eine Datei erstellt worden
ist. Was mich halt schon gewundert hat, weil wenigstens eine leere Datei hätte erstellt werden müssen.
Sehe ich auch so, zumal es hier mit deinem Beispiel-Text und auch mit Sonderzeichen (aber nicht im Kommentar) funktioniert hat.ist. Was mich halt schon gewundert hat, weil wenigstens eine leere Datei hätte erstellt werden müssen.
Diese Version kommt zumindest auch mit
<|>
in Kommentaren klar::: Peter8810.cmd::::::::::::::::::::::::::::::::::::::::::::::::::::::
:: LotPings administrator.de 2010-07-19
@echo off & Setlocal
Set Inp="Input.txt"
Set Out="output.txt"
Type NUL >%Out%
If defined Flag Set "Flag="
For /f "delims=" %%A in (
'Findstr /I "^//.*//$ ^proc" %Inp%'
) Do Set "Line=%%A" & Call :ProcLine
Pause
Goto :eof
:ProcLine
Echo."%Line%"| Findstr "^.//-*.*(.*).-*//.$" >NUL 2>&1 && Set Flag=Ok
If not defined Flag goto :Eof
Set "Line=%Line:|=^|%"
Set "Line=%Line:<=^<%"
Set "Line=%Line:>=^>%"
Echo.%Line%
>>%Out% Echo.%Line%
If /I "%Line:~0,4%" EQU "proc" Set "Flag="
Gruß
LotPings

Zitat von @peter8810:
der Code funktioniert super! Blöcke mit "---- Text ... bis ... proc Text" werden rausgefiltert
Schön wenn es klappt.der Code funktioniert super! Blöcke mit "---- Text ... bis ... proc Text" werden rausgefiltert
Das Flag wird gesetzt wenn eine Zeile mit- anfängt und irgendwas Klammer auf irgendwas Klammer zu, beliebige Anzahl - und // folgt.
Zurückgesetzt nach einer Zeile diemit proc beginnt.
%<---->%
Ein paar Fragen hab ich noch:
Zeile 8: In der For-Schleife wird die Inputdatei mit findstr durchsucht, richtig?
Wird dann jede gefundene Zeile weitergegeben (mit dem Call) oder wie funktioniert das?
Ja, durch die Einklammerung in ' wird die Ausgabe des Findstring Befehls Zeile für Zeile an den Do Teil weitergereicht.Zeile 8: In der For-Schleife wird die Inputdatei mit findstr durchsucht, richtig?
Wird dann jede gefundene Zeile weitergegeben (mit dem Call) oder wie funktioniert das?
Einzelheiten kriegst du mit
For /?
aber das musst du dir mehrmals zu Gemüte führen bis es Sinn ergibt.Zeile 14: Hier wird gesagt, das alles folgende geschrieben werden soll?
Wie oben erwähnt wird das Flag gesetztm ab jetzt beachten.Was bedeutet: >NUL 2>&1?
Da diese Zeile ja nur ein Test ist, brauchen wir weder die normale Ausgabe >NUL noch wollen wir ggfs störendeFehlermeldungen sehen, 2>&1 leitet die Fehlerausgabe um in die normale Ausgabe die ja schon im Scharzen Loch NUL versennkt wird.
Das nicht von dir erwähnte && führt den folgenden Befehl nur aus wenn der vorherige Findstr erfolgreich war.
Damit die Sonderzeichen diese Zeile 14 unbeschädigt passieren können habe ich beim Echo %Line% in Anführungszeichen gesetzt (und im findstr für diese zusätzlichen Zeichen einen Punkt eingfügt - wobei ich auch ein \" als escapetes Anführungszeichen hätte nehmen können)
Vielen Dank für die Top Hilfe!
Gruß
LotPings
Gruß
LotPings

Sorry Peter,
das sind jetzt ganz andere Anforderungen (auch kaum lesbare),
die dazu notwendigen komplexen RegEx überschreiten IMO die Fähigkeiten von Findstr. (ggfs. geht es mit Gnu grep)
Außerdem wird die RegEx so unscharf das auch ungewünschte Zeilen matchen.
Gruß
LotPings
das sind jetzt ganz andere Anforderungen (auch kaum lesbare),
die dazu notwendigen komplexen RegEx überschreiten IMO die Fähigkeiten von Findstr. (ggfs. geht es mit Gnu grep)
Außerdem wird die RegEx so unscharf das auch ungewünschte Zeilen matchen.
Gruß
LotPings