|
black_tencate
Anmeldungsdatum: 27. März 2007
Beiträge: 11349
|
Hej, mit pdfgrep -rh --include "*.pdf" <Suchstring>
finde ich aus einer Menge von pdf-Dateien die Zeilen mit dem Suchstring. So weit so gut. Aus jeder Zeile möchte ich aber nur ganz bestimmte Teile auflisten: 02.05.2018 xxxxxxx <Suchstring> xxxxxx xxxxxxxx xxxxx -yyyyyyy und zwar die markierten, im letzen Fall "-" auch noch die folgenden Ziffern (unterschiedlich viele). Alles was hier mit "x" gezeigt ist (unterschiedlich lang) soll weg, und die Leerzeichen auch. Mit LOCalc klappt das eher eher solala wegen der unterschiedlich vielen Leerzeichen zwischen den erwünschten Anteilen. Leider weiß ich überhaupt kein Bescheid Gruß black tencate
|
|
TausB
Anmeldungsdatum: 26. November 2009
Beiträge: 1570
|
Können das "-" bzw. "<" oder ">" mehrmals - also auch innerhalb der "xxx" - vorkommen? Falls nicht: In LO-Calc (Der gesamte String steht in A1):
Falls die drei Teilergebnisse in einer Zelle stehen sollen, sind die einzelnen Formeln mit "&" zu verbinden.
|
|
black_tencate
(Themenstarter)
Anmeldungsdatum: 27. März 2007
Beiträge: 11349
|
Hej TausB, TausB schrieb: Können das "-" bzw. "<" oder ">" mehrmals - also auch innerhalb der "xxx" - vorkommen? Falls nicht:
ich habe wohl mit <string> auf die falsch Fährte geführt, hätte string (ohne "<", ">") sein sollen. Durch geeignetes Haken-setzen unter "Trennoptionen" habe ich dann eher zufällig eine Variante, bei welcher im Ergebnis nur wenige Spalten "verrutscht" waren, bekommen. > Jedoch, mir schwebt halt immer noch eine Lösung im Terminal vor. <
In LO-Calc (Der gesamte String steht in A1):
*gins*, das erinnert mich stark meine Excelzeit, da habe ich mal m bzw n Elemente aus zwei Spalten zu einer zusammengefügt
Spalte E
WENN(WENN(WENN(REST(ZEILE(A1);m+n)=0;REST(ZEILE(A1)-1;m+n)+1;REST(ZEILE(A1);m+n))=WENN(REST(ZEILE(A1);n)=0;REST(ZEILE(A1)-1;n)+1;REST(ZEILE(A1);n));WENN(REST(ZEILE(A1);m+n)=0;REST(ZEILE(A1)-1;m+n)+1;REST(ZEILE(A1);m+n));WENN(REST(ZEILE(A1);m+n)=0;REST(ZEILE(A1)-1;m+n)+1;REST(ZEILE(A1);m+n))-n)<=0;WENN(WENN(REST(ZEILE(A1);m+n)=0;REST(ZEILE(A1)-1;m+n)+1;REST(ZEILE(A1);m+n))=WENN(REST(ZEILE(A1);n)=0;REST(ZEILE(A1)-1;n)+1;REST(ZEILE(A1);n));WENN(REST(ZEILE(A1);m+n)=0;REST(ZEILE(A1)-1;m+n)+1;REST(ZEILE(A1);m+n));WENN(REST(ZEILE(A1);m+n)=0;REST(ZEILE(A1)-1;m+n)+1;REST(ZEILE(A1);m+n))-n)+n;WENN(WENN(REST(ZEILE(A1);m+n)=0;REST(ZEILE(A1)-1;m+n)+1;REST(ZEILE(A1);m+n))=WENN(REST(ZEILE(A1);n)=0;REST(ZEILE(A1)-1;n)+1;REST(ZEILE(A1);n));WENN(REST(ZEILE(A1);m+n)=0;REST(ZEILE(A1)-1;m+n)+1;REST(ZEILE(A1);m+n));WENN(REST(ZEILE(A1);m+n)=0;REST(ZEILE(A1)-1;m+n)+1;REST(ZEILE(A1);m+n))-n)) Spalte F
WENN(m>=2;WENN(WENN(REST(ZEILE(A1);m+n)=0;REST(ZEILE(A1)-1;m+n);REST(ZEILE(A1);m+n))>n;x+y;x);WENN(n=1;WENN(REST(ZEILE(A1);m+n)=1;x;x+y);WENN(n=2;WENN(UND(n=2;m=1;GANZZAHL((ZEILE(A1))/(n+m))<>GANZZAHL((ZEILE(A1)-1)/(n+m)));x+y;x);WENN(GANZZAHL((ZEILE(A1))/(n+m))<>GANZZAHL((ZEILE(A1)-1)/(n+m));x+y;x)))))) spalte G
INDIREKT(ADRESSE(E1+GANZZAHL((ZEILE(A1)-1)/(n+m))*WENN(WENN(REST(ZEILE(A1);m+n)=0;REST(ZEILE(A1)-1;m+n)+1;REST(ZEILE(A1);m+n))>n;m;n);F1;;;"tabelle2")) das hatte (ich glaube das war s.Z. seahawk1986) mir dann sehr elegant "auseinander genommen" Gruß blacktencate
|
|
ChickenLipsRfun2eat
Anmeldungsdatum: 6. Dezember 2009
Beiträge: 12067
|
Hallo! Kannst du nicht pdfgrep mit -o/--only-matching aufrufen? Oder widerspricht das den tatsächlichen Zeilen? Das gibt ja wie in grep dann nur den gewünschten Teil aus. Alternativ durch awk jagen, nur $1, $3 und $NF ausgeben.
pdfgrep -rh --include "*.pdf" <Suchstring> | awk -F' ' '{ print $1 $2 $NF }'
|
|
black_tencate
(Themenstarter)
Anmeldungsdatum: 27. März 2007
Beiträge: 11349
|
Hej ChickenLipsRfun2eat, ChickenLipsRfun2eat schrieb: Hallo! Kannst du nicht pdfgrep mit -o/--only-matching aufrufen? Oder widerspricht das den tatsächlichen Zeilen? Das gibt ja wie in grep dann nur den gewünschten Teil aus. Alternativ durch awk jagen, nur $1, $3 und $NF ausgeben.
pdfgrep -rh --include "*.pdf" <Suchstring> | awk -F' ' '{ print $1 $2 $NF }'
leider paßt das auch nicht besser, weil sich die Zeilen unterscheiden
01.04.2019 xxxxxxxx / suchstring xx xx xx xx -25,00
02.01.2015 xxxxxxxxxxxxxxxxxxxx suchstring xx xx xx -25,00 Gruß black tencate
|
|
seahawk1986
Anmeldungsdatum: 27. Oktober 2006
Beiträge: 11278
|
Verstehe ich das richtig, dass am Zeilenanfang immer ein Datum im Format dd.mm.YYYY steht und am Ende der Zeile ein negativer Dezimalbetrag?
Dann könnte man das so machen:
$ sed -nE 's/[[:space:]]*([0-9][0-9]\.[0-9][0-9]\.[0-9][0-9][0-9][0-9]).*(suchstring).*(-[0-9]{1,},[0-9][0-9])/\1\t\2\t\3/p' << EOF
01.04.2019 xxxxxxxx / suchstring xx xx xx xx -25,00
02.01.2015 xxxxxxxxxxxxxxxxxxxx suchstring xx xx xx -25,00
EOF
01.04.2019 suchstring -25,00
02.01.2015 suchstring -25,00
|
|
black_tencate
(Themenstarter)
Anmeldungsdatum: 27. März 2007
Beiträge: 11349
|
Hej seahawk1986, seahawk1986 schrieb: Verstehe ich das richtig
im Prinzip ja, ich glaube aber, es wäre besser, ich verstünde mehr als nur, daß mit
a. ([0-9][0-9]\.[0-9][0-9]\.[0-9][0-9][0-9][0-9]) das Datum, und entsprechend mit b. (-[0-9]{1,},[0-9][0-9]) die negative Zahl mit 2 Nachkommastellen gemeint ist. Ferner reime ich mir zusammen c. s/[[:space:]] (?) laß die spaces aus (?) und d. \1\t\2\t\3/p print a 2=suchstring c (was ist t ?)
Und dann die ganz spannende Frage: Wie/was packe ich ins Terminal
sed -nE 's/[[:space:]]*([0-9][0-9]\.[0-9][0-9]\.[0-9][0-9][0-9][0-9]).*(suchstring).*(-[0-9]\.[0-9][0-9][0-9],[0-9][0-9])/\1\t\2\t\3/p' << EOF das führende "$" gehört da wohl nicht hin?
daran den print von pdfgrep -rh --include "*.pdf" <suchstring> anhängen
Du siehst, ich habe keinen blassen Schimmer, und wenn ich so bei man sed blättere, kommen mir leider auch nicht so die rechten Erleuchtungen. Gruß black tencate Und 'ne neue Tastatur für diesen refurbished T520 muß wohl auch mal her (shift rechts und space nur noch mit Gewalt!).
|
|
seahawk1986
Anmeldungsdatum: 27. Oktober 2006
Beiträge: 11278
|
Das führende $ symbolisiert einen Shell-Prompt, bei dem man einen Befehl eingibt (damit man das besser von Zeilen mit Ausgabe unterscheiden kann). Die Konstruktion << EOF bis zum nächten EOF ist ein Heredoc, damit kann man einem Programm Eingaben aus einer ad-hoc Datei (die man als Teil des Befehls eingibt) unterschieben. Du kannst die Ausgabe von pdfgrep per Pipe (vgl. Shell/Umleitungen) an den sed-Befehl weiterleiten:
| pdfgrep -rh --include "*.pdf" 'suchstring' | sed -nE 's/[[:space:]]*([0-9][0-9]\.[0-9][0-9]\.[0-9][0-9][0-9][0-9]).*(suchstring).*(-[0-9]{1,},[0-9][0-9])/\1\t\2\t\3/p'
|
Zu den Fragen bei der sed-Syntax:
[[:space:]]* matcht 0 oder mehr ASCII-Whitespace-Zeichen
\t ist ein Tab - wenn dir ein anderes Trennzeichen lieber ist, kannst du das natürlich stattdessen verwenden
|
|
black_tencate
(Themenstarter)
Anmeldungsdatum: 27. März 2007
Beiträge: 11349
|
Hej seahawk1986, seahawk1986 schrieb: Das führende $ symbolisiert einen Shell-Prompt, bei dem man einen Befehl eingibt (damit man das besser von Zeilen mit Ausgabe unterscheiden kann). Die Konstruktion << EOF bis zum nächten EOF ist ein Heredoc, damit kann man einem Programm Eingaben aus einer ad-hoc Datei (die man als Teil des Befehls eingibt) unterschieben. Du kannst die Ausgabe von pdfgrep per Pipe (vgl. Shell/Umleitungen) an den sed-Befehl weiterleiten:
| pdfgrep -rh --include "*.pdf" 'suchstring' | sed -nE 's/[[:space:]]*([0-9][0-9]\.[0-9][0-9]\.[0-9][0-9][0-9][0-9]).*(suchstring).*(-[0-9]{1,},[0-9][0-9])/\1\t\2\t\3/p'
|
paßt, danke, eine Frage hätte ich noch (-[0-9]{1,} "[0-9]" ok, aber "{1,}" ❓ Also z.B. nicht nur -25,00 sondern auch 1.177,25
Zu den Fragen bei der sed-Syntax:
gibt 's da was verständlichereches als man Gruß black tencate
|
|
seahawk1986
Anmeldungsdatum: 27. Oktober 2006
Beiträge: 11278
|
black_tencate schrieb: eine Frage hätte ich noch (-[0-9]{1,} "[0-9]" ok, aber "{1,}" ❓
[0-9]{1,} sagt, dass es mindestens eine Zahl geben muss, damit er darauf matcht - man könnte das auch als [0-9]+ schreiben.
gibt 's da was verständlichereches als man
Es gibt das Handbuch für GNU sed: https://www.gnu.org/software/sed/manual/sed.html
Also z.B. nicht nur -25,00 sondern auch 1.177,25
Ich würde da eine Sprache bevorzugen, die mehr Struktur reinbringt, um ein Datum oder einen Betrag zu validieren - z.B. mit Python3:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20 | #!/usr/bin/env python3
import fileinput
import datetime
import locale
import sys
locale.setlocale(locale.LC_ALL, 'de_DE.UTF-8')
for line in fileinput.input(files=('-',)):
for s in sys.argv[1:]:
if s in line:
day, *_, amount = line.split()
try:
ts = datetime.datetime.strptime(day, "%d.%m.%Y")
value = locale.atof(amount)
except ValueError:
continue
else:
print(ts.date(), s, value, sep='\t') # Daten, die sich leichter in der Shell verarbeiten lassen
# print(day, s, amount, sep='\t') # wenn man die Daten unverändert beibehalten will
|
Das kann man dann als ausführbare Datei nutzen:
pdfgrep -rh --include "*.pdf" 'suchstring' | ./filter_lines.py 'suchstring'
Durch die Formatumwandlung (ISO-Datum, Punkt als Dezimaltrennzeichen und Verzicht auf Tausender-Trennzeichen) kann man dann auch leichter in der Shell weiterrechnen.
|
|
black_tencate
(Themenstarter)
Anmeldungsdatum: 27. März 2007
Beiträge: 11349
|
Hej seahawk1986, werde mal ein bißchen "studieren" was sed angeht. Auch den Vorschlag mit Python probiere ich noch aus, danke dafür. Ich setze derweil hier auf 'gelöst' Gruß black tencate EDIT.: gerade getestet, und zu 99% für gut befunden. Kleiner Haken: pdfgrep scheint sich nicht für den Schalter -i "zu interessieren", ein Suchstring "Abcde" liefert andere Ergebnisse als "ABCDE", trotz "-i"
|