Как удалить файл в папке кроме имен файлов в list.txt?

Сначала протестируйте его, чтобы убедиться, что он доступен и читаем:

if [ -f "filename" ] && [ -r "filename" ]; then
    var=$(<"filename")
fi

Тест -fпроверяет, ссылается ли filenameна обычный файл , а тест -rпроверяет, читается ли он вами.

1
10.11.2019, 18:38
4 ответа

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

cd /photo
ls -1 | grep -v -x -f nodeletelist.txt | xargs -d "\n" -P 0 rm -f

Если есть что-то еще в каталоге (подкаталоги или разные файлы, что я не предполагаю, поскольку Вы включаете свой txt в список )я бы использовал find I вместо ls(find. -maxdepth 1 -type f -name "*.jpg"например ).

1
20.08.2021, 10:53

Используя rsyncи переместите файлы в фиктивный -каталог to-delete, затем выполните безопасную -очистку:

  1. запустить rsyncкоманду ниже в сухом режиме (удалить --dry-run, если результат был хорошим)

    rsync --dry-run -v -d --remove-source-files      \
          --exclude='*/'                             \
          --exclude-from='/path/to/nodeletelist.txt' \
    /path/to/source /path/to/source/to-delete
    
  2. удалить каталог /path/to/source/to-delete, созданныйrsync(примечание:rsyncможет создать каталог последнего уровня в месте назначения, если он не существует)и файлы были перемещены туда после двойной проверки.

    rm -irv #/path/to/source/to-delete
    

объяснение rsyncвариантов:

# --dry-run              'dry run'
# -v                     'verbose'
# -d                     'override recursive'
# --remove-source-files  'sender removes synchronized files (non-dir)'
# --exclude='*/'         'exclude all directories'
# --exclude-from='...'   'exclude list of files reading from specified path'
2
20.08.2021, 10:53

Для указанного случая без пробелов в именах

rm $(join -v 1 <(ls *.jpg) <(sed '$ d' nodeletelist.txt))

Предполагая, что последняя строка файла nodeletelist.txt действительно читаетсяnodeletelist.txt

Если нет, то просто

rm $(join -v 1 <(ls *.jpg) nodelete.txt)

но выглядит неэлегантно...

0
20.08.2021, 10:53

Если zshявляется опцией, вы можете определить некоторый glob -, определяющий шелл-код, например.

 % cmd() { ! grep -q $REPLY./nodeletelist.txt ; } 

Затем (из каталога photo/)

 % ls
 10.jpg   1.jpg   2.jpg   3.jpg   4.jpg   5.jpg   6.jpg   7.jpg   8.jpg   9.jpg   nodeletelist.txt

 % ls *(+cmd)                                         
10.jpg  4.jpg  5.jpg  6.jpg  7.jpg  8.jpg  9.jpg

Выглядит нормально, давайте удалим

 % rm *(+cmd)

 % ls
1.jpg  2.jpg  3.jpg  nodeletelist.txt

Вероятно, существует более эффективная реализация, которая сначала отображает файл в массив, а затем проверяет, является ли $REPLYэлементом массива.

2
20.08.2021, 10:53

Теги

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