Объемный файл переименовывает, поддерживая метки времени, исключая некоторых

В Ubuntu 18.10 имеют beeen, использующий mmv для предварительного ожидания имен папок (дата) к именам файлов в нескольких папках ('-n' флаг здесь для рассмотрения результатов):

mmv -n './????-??-??*/*.*' './#1#2#3#4-#5#6-#7#8#9/#1#2#3#4#5#6#7#8-#10.#11'

который, например, преобразовывает:

./2018-12-11/DSC05287.ARW -> ./2018-12-11/20181211-DSC05287.ARW

Это также преобразовывает:

./2018-12-11/20181211-DSC05287.ARW -> ./2018-12-11/20181211-20181211-DSC05287.ARW

при поддержании меток времени.

Некоторые файлы были уже переименованы, некоторые не имеют.

Как я могу отфильтровать команду для исключения файлов, соответствующих шаблону - те, которые запускаются с 8-разрядного числа, сопровождаемого дефисом?

Или мне нужен другой подход?

0
задан 11 February 2019 в 08:04

1 ответ

Я не поклонник единых утилит переименования, таким образом, вот то, как я сделал бы это с помощью только "стандарт (GNU) оборудование", конкретно bash, find и mv.

Принятие Вы только интересуетесь файлами, которые являются одним каталогом, уравнивает (так find -maxdepth 2), и специфически игнорирующие файлы, которые были уже ранее переименованы (но выполнение проверки работоспособности с regex обратными ссылками, чтобы не делать предположения):

find -regextype egrep -maxdepth 2 -type f \! -regex '\./([0-9]{4})-([0-9]{2})-([0-9]{2}).*/\1\2\3-.+' | while read f; do

  if [[ $f =~ ^(\./([0-9]{4}-[0-9]{2}-[0-9]{2}).*)/(.+)$ ]]; then
    # The above regex groups its matches into:
    # ${BASH_REMATCH[1]} = the dir pathname
    # ${BASH_REMATCH[2]} = the date in the dir pathname (remember to strip its dashes)
    # ${BASH_REMATCH[3]} = the file name

    mv -v "$f" "${BASH_REMATCH[1]}"/"${BASH_REMATCH[2]//-}-${BASH_REMATCH[3]}"

  fi

done

И зафиксировать тех, которые уже были неправильно "дважды датированы" (снова, с помощью обратных ссылок, чтобы не делать неоправданные предположения):

find -regextype egrep -maxdepth 2 -type f -regex '\./([0-9]{4})-([0-9]{2})-([0-9]{2}).*/\1\2\3-\1\2\3-.+' | while read f; do

  if [[ $f =~ ^(\./.+)/([0-9]{8})-[0-9]{8}-(.+)$ ]]; then
    # The above regex groups its matches into:
    # ${BASH_REMATCH[1]} = the dir pathname
    # ${BASH_REMATCH[2]} = the first date chunk
    # ${BASH_REMATCH[3]} = the filename "tail"

    mv -v "$f" "${BASH_REMATCH[1]}/${BASH_REMATCH[2]}-${BASH_REMATCH[3]}"

  fi

done

Дальнейшее чтение:

2
ответ дан 26 October 2019 в 06:57

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

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