mit dateinamen-teilen arbeiten
mit dateinamen-teilen arbeiten
hallo, ich sitze gerade vor einem kleinen shell-script, das mit dateien etwas macht. ich stehe gerade vor dem problem, das ich zb aus dem dateinamen "backup_2xy49.rar" nur den dateinamen OHNE extension filtern kann, und damit weiterarbeiten kann... grep viel mir spontan ein, da es sich eigentlich nur um eine regexp anwendung handeln kann (da die regeln nicht immer so simpel sein können). ich bin zwar kein anfänger in sachen regexp, aber mir fehlt einfach das passende tool, das mit strings arbeitet, und mir nur den teil zurückgibt, auf den die regexp matcht. wie gesagt, grep eignet sich nicht dafür, da das ding gleich die ganze zeile zurückgibt...
gibt mir nen programm-tipp wenn ihr eins kennt!
danke
gibt mir nen programm-tipp wenn ihr eins kennt!
danke
Die Shell kann das auch alleine
Code: Alles auswählen
#!/bin/bash
DATEI=backup_2xy49.rar
NAME=${DATEI%%.rar} && echo $NAME
backup_2xy49
EXTENSION=${DATEI#*.} && echo $EXTENSION
rar
danke, schonwieder was gelernt, kannst mir auch noch sagen, wie sich das verfahren nennt, damit ich mich auf ner man-page informieren kann?
nichtsdestotrotz würde ich auch gerne eine variante an der hand haben, um das mit regexp zu lösen, denn nicht immer lässt es sich so einfach lösen, wenn man verschieden variierende dateinamen hat, wo man eventuell vorne etwas wegschneiden muss, oder in der mitte...
ich denke da an den fall mit den rar dateien, das alte volume-format war ja
xy.rar
xy.r00
sy.r01
...
das neue sieht so aus
sy.part1.rar
sy.part2.rar
...
bei dem neuen format würde ich auch gern .part*.rar wegschneiden. wie müsste das dann lauten?
danke
nichtsdestotrotz würde ich auch gerne eine variante an der hand haben, um das mit regexp zu lösen, denn nicht immer lässt es sich so einfach lösen, wenn man verschieden variierende dateinamen hat, wo man eventuell vorne etwas wegschneiden muss, oder in der mitte...
ich denke da an den fall mit den rar dateien, das alte volume-format war ja
xy.rar
xy.r00
sy.r01
...
das neue sieht so aus
sy.part1.rar
sy.part2.rar
...
bei dem neuen format würde ich auch gern .part*.rar wegschneiden. wie müsste das dann lauten?
danke
hab mir eben mal einen RE ausdruck überlegt:
er müsste bei allen diesen dateien, wenn man den inhalt des ersten klammernpaars "(.*?)" ausgibt
bin schon am verzweifeln
Code: Alles auswählen
(.*?)(\.part[0-9]+)?\.rar
immer "bla" zurückliefern, also den dateinamen... fehlt mir nur noch ein tool, das diesen ausdruck korrekt umsetzt... hab diesen ausdruck bereits mit einem regex-debugger getestet, dieser ausdruck ist 100%ig richtig!bla.part1.rar
bla.rar
bla.part02.rar
bla.part005.rar
bin schon am verzweifeln

-
- Beiträge: 441
- Registriert: 12.10.2005 23:09:28
- Lizenz eigener Beiträge: MIT Lizenz
-
Kontaktdaten:
Du suchst "sed"!
Ein kleines Minimalbeispiel, das mit einer einfacheren regexp arbeitet und ungefähr das machst was du willst ist:
Die liste von Dateinamen mit Endungen einfach "durchpipen".
Ein kleines Minimalbeispiel, das mit einer einfacheren regexp arbeitet und ungefähr das machst was du willst ist:
Code: Alles auswählen
sed 's/\(.*\)\.rar/\1/'
"Linux supports the notion of a command line or a shell for the same reason that only children read books with only pictures in them." - Bill Garrett
danke, dachte schon, ich müsst mir nen neues board suchen, weil ich so selten antworten auf meine fragen bekomme 
btt: ich dachte schon, ich wäre am ziel
hab mal meinen ausdruck sed-konform gemacht, scheint aber nich zu klappen...
wie man sieht, klappts mit xyz.rar, aber bei dem part1 dazwischen willer mir das immer wieder mit aufdrücken. haste da eventuell eine idee?

btt: ich dachte schon, ich wäre am ziel
hab mal meinen ausdruck sed-konform gemacht, scheint aber nich zu klappen...
Code: Alles auswählen
echo "www.part1.rar" "xyz.rar" | sed -e 's/\(.*\?\)\(\.part[0-9]\+\)\?\.rar/\1/'
www.part1.rar xyz
Ich vermute stark, dass das Problem ist, dass beide Strings in einer Zeile sind!ali hat geschrieben:wie man sieht, klappts mit xyz.rar, aber bei dem part1 dazwischen willer mir das immer wieder mit aufdrücken. haste da eventuell eine idee?Code: Alles auswählen
echo "www.part1.rar" "xyz.rar" | sed -e 's/\(.*\?\)\(\.part[0-9]\+\)\?\.rar/\1/' www.part1.rar xyz
Mach mal eine geeignente Eingabe (Stings in eine Textdatei schreiben, oder `ls *.*' oder so) dann sollte es auch funzen.
Will auch noch ein bisschen Code dazu werfen:
Code: Alles auswählen
ls *.* | sed -e 's/\.part[0-9]\+// ; s/\.rar//'
Use ed once in a while!
ein echo "www.part1.rar" habich auch versucht, es kam immer ein string mit dem "part1" zurück, mir scheint es fast so, als würde sed das von mir definierte lazy "\(.*\?\)" (das "?") ignorieren, und bis hinter part1 parsen, dann den teil "\(\.part[0-9]\+\)\?" komplett ignorieren (also ? bedeutet 0 oder 1mal, sed nimmt hier wohl 0, weil es schon hinter dem part angekommen ist) und macht dann bei .rar weiter...Meillo hat geschrieben:Ich vermute stark, dass das Problem ist, dass beide Strings in einer Zeile sind!ali hat geschrieben:wie man sieht, klappts mit xyz.rar, aber bei dem part1 dazwischen willer mir das immer wieder mit aufdrücken. haste da eventuell eine idee?Code: Alles auswählen
echo "www.part1.rar" "xyz.rar" | sed -e 's/\(.*\?\)\(\.part[0-9]\+\)\?\.rar/\1/' www.part1.rar xyz
Mach mal eine geeignente Eingabe (Stings in eine Textdatei schreiben, oder `ls *.*' oder so) dann sollte es auch funzen.
falls jemand dazu ne erklärung hat, wäre interessant zu wissen, wieso sed das macht, was es macht

das klappt, okay, daran hatte ich nicht gedacht, man lernt immer wieder was dazuMeillo hat geschrieben: Will auch noch ein bisschen Code dazu werfen:(Das entfernt jeweils nur den entsprechenden Teil des Strings ... finde ich einfach zu handhaben.)Code: Alles auswählen
ls *.* | sed -e 's/\.part[0-9]\+// ; s/\.rar//'

danke
... das war der Grund weshalb ich meine "einfachere" Lösung vorgeschlagen habe, denn RegExp sind nicht trivial.ali hat geschrieben:ein echo "www.part1.rar" habich auch versucht, es kam immer ein string mit dem "part1" zurück, mir scheint es fast so, als würde sed das von mir definierte lazy "\(.*\?\)" (das "?") ignorieren, und bis hinter part1 parsen, dann den teil "\(\.part[0-9]\+\)\?" komplett ignorieren (also ? bedeutet 0 oder 1mal, sed nimmt hier wohl 0, weil es schon hinter dem part angekommen ist) und macht dann bei .rar weiter...
falls jemand dazu ne erklärung hat, wäre interessant zu wissen, wieso sed das macht, was es macht
Der Teil der den "part" matchen soll, bleibt leer, weil die erste Klammer gleich alles für sich wegnimmt. RegExp sind standardmäßig "greedy" also "gierig", sie nehmen was sie kriegen. Das ? stellt ja offen, ob der Ausdruck davor vorkommt, oder nicht. Der RegExp passt nunmal auf zwei Arten, einmal wenn der Part-Teil in die erste Klammer fällt und die zweite gar nicht vorkommt, und einmal, wenn der Part-Teil in die zweite Klammer fällt.
... kappiert?
deshalb sollte man bei optionalen Elementen etwas mehr aufpassen und lieber alternative Lösungen wählen.
Use ed once in a while!
standardmäßig greedy, jo, schon klar, aber das fragezeichen hat zwei bedeutungen, einmal kann es bedeuten, das das element davor 0 oder 1 mal vorkommen darf, und einmal, wenn es hinter einem quantifier steht, das dieser quantifier lazy wird (bei mir also hinter dem * in der ersten klammer!), so müsste mein regexp eigentlich anders matchen, denn die abstrakte maschine müsste eigentlich bei einem lazy-quatifier nach jedem buchstaben versuchen, ob nich die nachfolgenden definitionen auch passen... aber nungut, sollte ich einfach als schlamperei abhaken und gut istMeillo hat geschrieben:RegExp sind standardmäßig "greedy" also "gierig", sie nehmen was sie kriegen. Das ? stellt ja offen, ob der Ausdruck davor vorkommt, oder nicht. Der RegExp passt nunmal auf zwei Arten, einmal wenn der Part-Teil in die erste Klammer fällt und die zweite gar nicht vorkommt, und einmal, wenn der Part-Teil in die zweite Klammer fällt.
... kappiert?

deine version is auch die elegantere, weil die die teile, sofern sie vorkommen, rauslöscht, so kann man es noch beliebig erweitern, zb .zip, .tar.gz etc

danke
ahh,,, da hab ich nicht genau genug geschaut und auch auch deinen vorherigen Post nicht gut genug gelesenali hat geschrieben:standardmäßig greedy, jo, schon klar, aber das fragezeichen hat zwei bedeutungen, einmal kann es bedeuten, das das element davor 0 oder 1 mal vorkommen darf, und einmal, wenn es hinter einem quantifier steht, das dieser quantifier lazy wird (bei mir also hinter dem * in der ersten klammer!), so müsste mein regexp eigentlich anders matchen, denn die abstrakte maschine müsste eigentlich bei einem lazy-quatifier nach jedem buchstaben versuchen, ob nich die nachfolgenden definitionen auch passen... aber nungut, sollte ich einfach als schlamperei abhaken und gut ist

... ich weiß nicht, ob sed (vermutlich gsed in unserem Fall) das unterstützt, also das Fragezeichen als ungreedy-Modifier ... aber falls es unterstützt wird, sollte es eigentlich wie von dir beschrieben ausgewertet werden (klingt jedenfalls logisch, in meinen Ohren)
man darf aber auch nicht vergessen, dass meine Version die Position der Teilstücke im String _nicht_ berücksichtigt, wohingegen das andere Pattern, dies sehr wohl tut!deine version is auch die elegantere, weil die die teile, sofern sie vorkommen, rauslöscht, so kann man es noch beliebig erweitern, zb .zip, .tar.gz etc
Für deinen Fall ist das wohl unerheblich ... nur sollte man es nicht vergessen.
hat mir viel Spaß gemachtdanke

Use ed once in a while!
na, das habich ja direkt erweitert, bei mir berichtigt das nun auch die position, und zwar ists bei mir das ende des strings:Meillo hat geschrieben:man darf aber auch nicht vergessen, dass meine Version die Position der Teilstücke im String _nicht_ berücksichtigt, wohingegen das andere Pattern, dies sehr wohl tut!
Für deinen Fall ist das wohl unerheblich ... nur sollte man es nicht vergessen.
Code: Alles auswählen
sed -e 's/\.rar$// ; s/\.zip$// ; s/\.part[0-9]\+$//'

und es funktioniert
