Рекурсивно сравните количества определенных файлов между двумя каталогами

Я искал и искал, но не нашел ответ на этот вопрос.

Вот сценарий: Я просто разорвал свой весь набор CD к бесплатному кодеку без потерь (FLAC) для архива. У меня также есть некоторый высококачественный .m4a с потерями ИЛИ .mp3 в этом архиве. Это хранится в DIRECTORY01/artist - альбом / *.flac структура. Все соответствующие файлы в этом каталоге являются или .flac, .m4a или .mp3

Затем я транскодировал этот весь каталог к ogg vorbis для фактического ежедневного использования и для моего портативного медиаплеера. Это хранится в DIRECTORY02/artist - альбом / *.ogg структура. Все соответствующие файлы являются .ogg.

Теперь я хочу проверить, что все хорошо. Я использовал разность для сравнения количества папок (и проверить, что они - то же. Затем я считал количество flac и ogg файлов (соответственно) в каждом.

Проблема: существует три дополнительных .ogg файла в .ogg папке, так или иначе, где-нибудь. Поскольку каждый родительский каталог содержит 526 подпапок, я хотел бы знать, как автоматически определить каталоги, которые отличаются только по количеству файла определенного .ogg или типов файлов .flac/.m4a/.mp3 (игнорирующий любой .txt, .log, .nfo, .cue, .jpg, и т.д.).

Так идеально безотносительно команды (команд) я работаю, результатом был бы отчет, который игнорирует общие подкаталоги с количествами общего файла и помогает мне определить конкретно любые каталоги, которые имеют отличие ".ogg или .flac/.m4a/.mp3" количества файла.

Действительно ли это возможно? Я также открыт для других предложений/логик для проверки что все X количества .flac/.m4a/.mp3, успешно транскодированного к .ogg.

3
задан 24 March 2019 в 11:47

3 ответа

Используя for цикл с find, это не может быть самым быстрым способом достигнуть Вашей цели, но должно работать правильно:

for dir in DIRECTORY01/*/ ; do fcount=$(find "$dir" -maxdepth 1 -type f \( -name '*.flac' -o -name '*.m4a' -o -name '*.mp3' \) -printf . | wc -c) ; ocount=$(find "${dir/DIRECTORY01/DIRECTORY02}" -maxdepth 1 -type f -name '*.ogg' -printf . | wc -c); if [[ "$fcount" -ne "$ocount" ]]; then echo "$dir has $fcount .flac .m4a and .mp3 files but ${dir/DIRECTORY01/DIRECTORY02} has $ocount .ogg files" ; fi ; done

Или больше четко

for dir in DIRECTORY01/*/ ; do
  fcount=$(find "$dir" -maxdepth 1 -type f \( -name '*.flac' -o -name '*.m4a' -o -name '*.mp3' \) -printf . | wc -c)
  ocount=$(find "${dir/DIRECTORY01/DIRECTORY02}" -maxdepth 1 -type f -name '*.ogg' -printf . | wc -c)
  if [[ "$fcount" -ne "$ocount" ]]; then
    echo "$dir has $fcount .flac .m4a and .mp3 files but ${dir/DIRECTORY01/DIRECTORY02} has $ocount .ogg files"
  fi
done

произведет что-то подобное:

DIRECTORY01/Nirvana - Nevermind/ has 12 .flac files but DIRECTORY02/Nirvana - Nevermind/ has 11 .ogg files

Для каждого каталога, где количества файла не соответствуют. Цикл корректно не обработает состояния ошибки, такие как каталог 'Artist - Album', появляющийся в DIRECTORY01, но не в DIRECTORY02 или различиях в написании каталога 'Album - Artist'.

2
ответ дан 1 December 2019 в 15:34

Вы могли бы попытаться использовать meld. Описание:

Комбинация является графическим различным средством просмотра и приложением слияния для рабочего стола GNOME. Это поддерживает 2 и diffs с 3 файлами, рекурсивный каталог diffs, diffing каталогов при управлении версиями (Базар, Кодевилл, CVS, Darcs, Окаменелость SCM, Мерзавец, Подвижный, Монотонный, Подверсия), а также способность к вручную, и автоматически объедините различия в файле.

1) веб-сайт:

http://meldmerge.org/

2) И если это находится в Вашем списке репозиториев, можно установить его с:

sudo apt-get update
sudo apt-get install meld

3) Это находится также в приложении программного обеспечения Ubuntu.

0
ответ дан 1 December 2019 в 15:34

Так как у Вас есть больше .ogg, чем .flac, простой подход должен был бы найти весь *.ogg имена и проверить, которые не имеют соответствия .flac имя. Что-то как:

find DIRECTORY02/ -type f -name '*ogg' -print0 | 
    while IFS= read -r -d '' f; do 
        flac="${f//.ogg/.flac}"; 
        flac="${flac##DIRECTORY02/}"; 
        [[ -e DIRECTORY01/"$flac" ]] || 
            printf "Missing file: %s\n" "$flac"; 
done

Вот то же самое как прокомментированный сценарий:

#!/bin/bash

## find all files in DIRECTORY02/ whose name ends in .ogg
find DIRECTORY02/ -type f -name '*.ogg' -print0 | 
    ## Iterate over the results of the find command, saving
    ## each file as "$f". The fancy -print0 and read -d '' stuff
    ## is needed to deal with filenames that can contain newlines.
    while IFS= read -r -d '' f; do 
        ## create the new $flac variable which is $f but with ".flac"
        ## instead of ".ogg"
        flac="${f//.ogg/.flac}"; 
        ## remove the "DIRECTORY02/" from the $flac variable. If
        ## the "$f" variable was 'DIRECTORY02/artist - album/file.ogg'
        ## it is now 'artist - album/file.flac'.
        flac="${flac##DIRECTORY02/}"; 
        ## Check whether the file exists in the same subdirectory under
        ## DIRECTORY01
        [[ -e DIRECTORY01/"$flac" ]] || 
            ## If it doesn't, print
            printf "Missing file: %s\n" "$flac"; 
done
3
ответ дан 1 December 2019 в 15:34

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

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