it-swarm.com.de

Wie kann ich Dateien nach Dateierweiterung rekursiv kopieren und dabei die Verzeichnisstruktur beibehalten?

An der Linux-Befehlszeile möchte ich einen (sehr großen) Satz von .txt-Dateien von einem Verzeichnis (und seinen Unterverzeichnissen) in ein anderes kopieren.

Ich brauche die Verzeichnisstruktur, um intakt zu bleiben, und ich muss Dateien mit Ausnahme derjenigen, die mit .txt enden, ignorieren.

71

Verwenden Sie dazu find und cpio

cd /top/level/to/copy
find . -name '*.txt' | cpio -pdm /path/to/destdir

(-updm for overwrite destination content.)
94
Iain
cd /source/path
find -type f -name \*.txt -exec install -D {} /dest/path/{} \;
7
sborsky

Ein anderer Ansatz

find . -name '*.txt' -exec rsync -R {} path/to/dext \;

2
Marc

Der einfachste Weg, der bei mir funktioniert hat:

cp --parents -R jobs/**/*.xml ./backup/

ein Haken ist, dass Sie zu dem "gewünschten" Verzeichnis navigieren müssen, bevor der "übergeordnete Pfad" korrekt ist.

Stellen Sie außerdem sicher, dass Sie rekursive Globs in bash aktiviert haben:

shopt -s globstar
1
icyerasor

Ich habe versucht, dasselbe unter macOS zu tun, aber keine der Optionen hat wirklich für mich funktioniert. Bis ich ditto entdeckt habe.

Ich musste viele .wav-Dateien kopieren und sie überspringen lassen.

find . -type f -iname "*.wav" -ls -exec ditto {} /destination/folder/{} \;

  • find . - Führt die Suche im aktuellen Ordner aus. Stellen Sie sicher, dass Sie cd /source/folder, bevor Sie beginnen

  • -type f - Gibt an, dass nur nach Dateien gesucht werden soll

  • -iname "*.wav" - Hiermit wird die Suche nach Groß- und Kleinschreibung * .wav eingeleitet
  • -ls - Hier sehen Sie die Datei, an der gearbeitet wird. Sonst zeigt es nichts.
  • -exec ditto {} /destination/folder/{} \; - Kopiert und erstellt alle Dateien mit demselben Verzeichnisbaum.
1

wie wäre es, wenn du es zuerst mit kopierst?

cp -r /old/folder /new/folder

dann gehe in den neuen Ordner und starte

find . -type f ! -iname "*.txt" -delete

oder nur

cp -r /old/folder /new/folder && find . -type f ! -iname "*.txt" -delete

Edit: ok du willst einen befehl der filtert (ich habe das nicht getestet weil mein system nicht den befehl cpio hat!). Hier habe ich es gefunden: http://www.gnu.org/software/findutils/manual/html_mono/find.html#Copying-A-Subset-of-Files

find . -name "*.txt" -print0 |
     cpio -pmd0 /dest-dir

Bitte testen Sie dies zuerst, da ich es noch nicht ausprobiert habe. Wenn jemand das überprüfen würde, wäre das großartig.

1
Dennis Hodapp

Zum Verzeichnis navigieren:

find . -regex '<regexp_to_get_directories_and_files_you_want>' | xargs -i cp -r --parents {} path/to/destination

Es ist etwas direkter und mächtiger, wenn Sie reguläre Ausdrücke verwalten.

0
keywalker