Перемещать файлы в каталоги в зависимости от их расширения [дубликат]

На этот вопрос уже есть ответ здесь:

У меня есть каталог с огромным количеством файлов с разными расширениями. Что я хочу сделать, так это переместить каждое расширение в папку с именем само расширение, и эти файлы без расширения переместятся в папку с именем unkown .

Например, у меня есть файлы a.txt , b.txt , a.pdf , b.pdf , a.mp4 , файл , новый файл ....

Результатом будет 4 каталога с именами txt , pdf , mp4 , unkonw

txt каталог содержит файлы a.txt , b.txt

каталог pdf содержит файлы a.pdf , ] b.pdf

каталог mp4 содержит файлы a.mp4

каталог unkonw содержит файлы файл , ] новый файл

4
задан 30 May 2015 в 13:13

2 ответа

Вот иначе:

mkdir -p unknown; 
for f in *; do 
[[ $f =~ \. ]] && mkdir -p "${f##*.}" && 
               mv "$f" "${f##*.}"/ || 
mv "$f" unknown/; done

Объяснение

  • && означает, "выполняет команду справа, только если команда слева была успешна".
  • || означает, "выполняет команду справа, только если команда слева перестала работать". Эти два объединенные символа могут работать как if/else блок.
  • mkdir -p unknown; : создайте unknown каталог. -p есть ли так, чтобы mkdir не будет жаловаться, существует ли каталог.
  • for f in * : для всех файлов и каталогов в текущем каталоге.
  • [[ $f =~ \. ]] && : если текущее имя файла/dir содержит a ., если это имеет расширение, то...
  • mkdir -p "${f##*.}"/ : конструкция ${var##pat} удалит самое долгое соответствие pat с начала переменной $var. Здесь, pat что-либо до точки, таким образом, это оставит только расширение. Эта команда, поэтому, создает каталог расширения, если это не существует.
  • mv "$f" "${f##*.}"/ : mv затем перемещает файл в соответствующий каталог. || mv "$f" unknown/; : если предыдущая команда перестала работать (если этот файл/каталог), не имеет расширения, перемещают его в unknown.

Обратите внимание, что это распечатает это сообщение об ошибке, но можно безопасно проигнорировать его:

mv: cannot move ‘unknown’ to a subdirectory of itself, ‘unknown/unknown’

Если необходимо переместить только файлы, и никакие каталоги (команды выше также переместят названный каталог dir.foo в foo/), используйте это вместо этого:

mkdir -p unknown; 
for f in *; do 
[[ -f $f ]] && 
    if [[ $f =~ \. ]]; then 
        mkdir -p "${f##*.}" && 
        mv "$f" "${f##*.}"/; 
    else mv "$f" unknown/; fi; 
done
6
ответ дан 30 May 2015 в 13:13

Этот bash сценарий сделает это: выполните его с bash script.sh <path> или ./script.sh <path>, где <path> путь к папке, содержащей файлы:

#!/bin/bash

for path in ${1}/*
do
    if [ -f "${path}" ]
    then
        extension="$(<<< "${file}" sed -rn 's/^.*\.(.*)$/\1/p')"
        if [ -n "${extension}" ]
        then
            mkdir -p "${1}/${extension}"
            mv "${path}" "${1}/${extension}"
        else
            mkdir -p "${1}/unknown"
            mv "${path}" "${1}/unknown"
        fi
    fi
done

tree вывод прежде и после выполнения сценария на tmp каталог:

ubuntu@ubuntu:~$ tree tmp
tmp
├── a.mp4
├── a.pdf
├── a.txt
├── b.pdf
├── b.txt
├── file
├── folder
└── newfile

1 directory, 7 files
ubuntu@ubuntu:~$ bash script tmp/
ubuntu@ubuntu:~$ tree tmp
tmp
├── folder
├── mp4
│   └── a.mp4
├── pdf
│   ├── a.pdf
│   └── b.pdf
├── txt
│   ├── a.txt
│   └── b.txt
└── unknown
    ├── file
    └── newfile

5 directories, 7 files
0
ответ дан 30 May 2015 в 13:13

Другие вопросы по тегам:

Похожие вопросы: