2

У меня есть множество каталогов (2005 - 2012), каждый с файлами (01.jpg - 100.jpg).

Если бы я захотел переименовать все файлы в базовый каталог, например, переименовать в Folder 2005 - 01.jpg, что было бы проще всего сделать из командной строки в Linux?

Например из

/home/mark/images/2005/01.jpg
/home/mark/images/2005/02.jpg
/home/mark/images/2005/03.jpg
/home/mark/images/2006/01.jpg
/home/mark/images/2006/02.jpg
/home/mark/images/2006/03.jpg

в

/home/mark/images/Folder 2005 - 01.jpg
/home/mark/images/Folder 2005 - 02.jpg
/home/mark/images/Folder 2005 - 03.jpg
/home/mark/images/Folder 2006 - 01.jpg
/home/mark/images/Folder 2006 - 02.jpg
/home/mark/images/Folder 2006 - 03.jpg

Наверняка для этого должен быть простой вкладыш? Я знаю, что вы можете использовать, например, {2005-2012} для доступа к нескольким каталогам, но я не уверен, как затем получить доступ к этому значению позже при переименовании.

3 ответа3

2
#!/bin/bash
for year in 20??; do
  pushd "$year"
  for file in *; do
    echo mv "$file" ../"Folder ${year} - ${file}"
  done
  popd
done

Удалите echo если вывод выглядит хорошо для вас.

2

Попробуйте это, если вы находитесь в каталоге с каталогами с 2005 по 2012):

start=$PWD
for directory in *; do
  cd "$directory"
  for filename in *; do
    mv "$filename" ../"Folder $directory - $filename"
  done
  cd "$start"
done

Или как вкладчик

start=$PWD; for directory in *; do cd "$directory"; for filename in *; do mv "$filename" ../"Folder $directory - $filename"; done; cd "$start"; done

Дерево ввода:

.
├── 2005
│   ├── 01.jpg
│   ├── 02.jpg
│   └── 03.jpg
├── 2006
│   ├── 01.jpg
│   ├── 02.jpg
│   └── 03.jpg

Дерево вывода:

.
├── 2005
├── 2006
├── Folder\ 2005\ -\ 01.jpg
├── Folder\ 2005\ -\ 02.jpg
├── Folder\ 2005\ -\ 03.jpg
├── Folder\ 2006\ -\ 01.jpg
├── Folder\ 2006\ -\ 02.jpg
└── Folder\ 2006\ -\ 03.jpg
0

Вероятно, у вас есть Perl, и поэтому в большинстве дистрибутивов также установлена команда prename (часто связанная с простым rename , например, в Debian и Ubuntu).

Если это так, то вы можете сделать это с помощью одной строки:

$ ls *
2005:
01.jpg  02.jpg  03.jpg

2006:
01.jpg  02.jpg  03.jpg
$ rename 's#(.+)/(.+)#Folder $1 - $2#' */*
$ ls -F1R
.:
2005/
2006/
Folder 2005 - 01.jpg
Folder 2005 - 02.jpg
Folder 2005 - 03.jpg
Folder 2006 - 01.jpg
Folder 2006 - 02.jpg
Folder 2006 - 03.jpg

./2005:

./2006:

Команда rename использует регулярное выражение, которое

  1. ловит имя файла до последнего разделителя каталогов / (например, 2005) и сохраняет его в $1
  2. ловит имя файла после последнего разделителя каталогов / (например, 01.jpg) и сохраняет его в $2
  3. переименовывает каждый файл в Folder $1 - $2 (например, Folder 2005 - 01.jpg).

Используйте rename -n чтобы увидеть, какие изменения будут внесены, прежде чем запускать команду по-настоящему.


Примечание: этот шаблон:

s#(.*?)([^/]+)/([^/]+)$#$1Folder $2 - $3#

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

Всё ещё ищете ответ? Посмотрите другие вопросы с метками .