it-swarm.com.de

Umbenennen von Dateien und Verzeichnissen rekursiv unter ubuntu/bash

Ich möchte alle Dateien und Verzeichnisse, die das Wort "Spezial" enthalten, in "regulär" umbenennen. Die Groß-/Kleinschreibung sollte beibehalten werden, damit "Spezial" nicht "regelmäßig" wird.

Wie kann ich das in bash rekursiv machen? 

53
Tom

Versuchen Sie dies (erfordern bash --version> = 4):

shopt -s globstar
rename -n 's/special/regular/' **

Entfernen Sie den Schalter -n, wenn Ihre Tests in Ordnung sind

warning  Es gibt andere Tools mit demselben Namen, die dies möglicherweise nicht können. Seien Sie also vorsichtig.

Wenn Sie den folgenden Befehl ausführen (GNU)

$ file "$(readlink -f "$(type -p rename)")"

und du hast ein ergebnis wie

.../rename: Perl script, ASCII text executable

und nicht enthaltend:

ELF

dann scheint dies das richtige werkzeug zu sein =)

Wenn nicht, machen Sie es zum Standard (normalerweise bereits der Fall) für Debian und leiten Sie es wie Ubuntu ab:

$ Sudo update-alternatives --set rename /path/to/rename

(Ersetzen Sie /path/to/rename durch den Pfad Ihres Perl's rename Befehls.


Wenn Sie diesen Befehl nicht haben, durchsuchen Sie Ihren Paketmanager, um ihn zu installieren, oder manuell


Last but not least wurde dieses Tool ursprünglich von Larry Wall, dem Vater von Perl, geschrieben.

73
Gilles Quenot

Eine Lösung mit find:

Um nur Dateien umzubenennen :

find /your/target/path/ -type f -exec rename 's/special/regular/' '{}' \;

Um nur Verzeichnisse umzubenennen :

find /your/target/path/ -type d -execdir rename 's/special/regular/' '{}' \+

Umbenennen von Dateien und Verzeichnissen :

find /your/target/path/ -execdir rename 's/special/regular/' '{}' \+
88
speakr

Wenn Sie nichts dagegen haben, ein anderes Tool zu installieren, können Sie rnm verwenden:

rnm -rs '/special/regular/g' -dp -1 *

Es wird alle Verzeichnisse/Unterverzeichnisse (wegen -dp -1) durchgehen und special durch regular im Namen ersetzen.

5
Jahid

@speakr's answer war der Schlüssel für mich.

Wenn Sie -execdir verwenden, um sowohl Dateien als auch Verzeichnisse zu transformieren, möchten Sie auch -type f aus dem angezeigten Beispiel entfernen. Um es zu buchstabieren, benutze:

find /your/target/path/ -execdir rename 's/special/regular/' '{}' \+

Erwägen Sie außerdem das Hinzufügen eines g (global) - Flags zum regulären Ausdruck, wenn Sie all - Vorkommen von special durch regular in einem bestimmten Dateinamen und nicht nur beim ersten Vorkommen ersetzen möchten. Zum Beispiel:

find /your/target/path/ -execdir rename 's/special/regular/g' '{}' \+

wandelt special-special.jpg in regular-regular.jpg um. Ohne das globale Flag erhalten Sie regular-special.jpg.

FYI: GNU Umbenennen ist unter Mac OSX nicht standardmäßig installiert. Wenn Sie den Paketmanager Homebrew verwenden, wird brew install rename Abhilfe schaffen.

2
U007D

Für diejenigen, die nur Verzeichnisse umbenennen möchten, können Sie diesen Befehl verwenden:

find /your/target/path/ -type d -execdir rename 's/special/regular/' '{}' \;

Der Notizentyp ist jetzt d für das Verzeichnis und verwendet -execdir.

Ich konnte jedoch nicht herausfinden, wie man Dateien und Verzeichnisse in einem einzigen Durchgang umbenennt.

Jemand hat zuvor kommentiert, dass der Stammordner nicht mehr durchlaufen werden konnte, nachdem er den Stammordner umbenannt hatte. Es steht ein -d-Schalter zur Verfügung, der von unten nach oben eine Tiefendurchquerung durchführt, so dass der Stamm zuletzt umbenannt wurde, glaube ich:

find -d /your/target/path/ -type d -execdir rename 's/special/regular/' '{}' \;

Aus der Manpage (man find):

 -d      Cause find to perform a depth-first traversal, i.e., directories are visited in post-order and all entries in a directory will be
         acted on before the directory itself.  By default, find visits directories in pre-order, i.e., before their contents.  Note, the
         default is not a breadth-first traversal.
0
LokMac

Hier ist ein anderer Ansatz, der portabler ist und nicht auf den Befehl rename angewiesen ist (da er je nach Distros möglicherweise andere Parameter erfordert).

Es benennt Dateien und Verzeichnisse rekursiv um:

find . -depth -name "*special*" | \
while IFS= read -r ent; do mv $ent ${ent%special*}regular${ent##*special}; done

Was es macht

  • verwenden Sie find mit dem Parameter -depth, um die Ergebnisse mit einem depth-first-Durchlauf neu anzuordnen (d. h. alle Einträge in einem Verzeichnis werden vor dem Verzeichnis selbst angezeigt).
  • führen Sie Mustersetzungen aus, um nur das letzte Vorkommen von regular im Pfad zu ändern.

Auf diese Weise werden die Dateien zuerst und dann jedes übergeordnete Verzeichnis geändert. 

Beispiel

Geben Sie den folgenden Baum:

├── aa-special-aa
│   └── bb-special
│       ├── special-cc
│       ├── special-dd
│       └── Special-ee
└── special-00

Es generiert diese mv-Befehle in dieser bestimmten Reihenfolge:

mv ./aa-special-aa/bb-special/special-cc ./aa-special-aa/bb-special/regular-cc
mv ./aa-special-aa/bb-special/special-dd ./aa-special-aa/bb-special/regular-dd
mv ./aa-special-aa/bb-special ./aa-special-aa/bb-regular
mv ./aa-special-aa ./aa-regular-aa
mv ./special-00 ./regular-00

Um den folgenden Baum zu erhalten:

├── aa-regular-aa
│   └── bb-regular
│       ├── regular-cc
│       ├── regular-dd
│       └── Special-ee
└── regular-00
0
jyvet