Попытка переименовать файлы с использованием двух файлов txt, но не дает правильных результатов - PullRequest
1 голос
/ 09 июля 2020

недавно просто пытался написать сценарий, чтобы я мог переименовать несколько файлов из двух файлов txt в правильном порядке, это вроде работает, но не дает результатов, которые я ищу.

Если кто-то может увидеть, что не так дайте мне знать об этом!

IFS=$'\n'
for i in $(cat ../temp/files.txt); for j in $(cat ../temp/filenames.txt); do mv $i $j; done

Ответы [ 3 ]

4 голосов
/ 09 июля 2020

У вас есть параллельные файлы, поэтому вы захотите читать из двух файлов одновременно в одном oop, а не во вложенных циклах. Когда у вас есть вложенные циклы, вы в конечном итоге будете читать второй файл снова и снова, по одному разу для каждой строки в первом файле. Один l oop, который читает из обоих файлов, будет проходить через них синхронно.

while IFS= read -u3 -r source && IFS= read -u4 -r target; do
    mv "$source" "$target"
done 3<../temp/files.txt 4<../temp/filenames.txt

Шаги:

  1. Часть после done фактически выполняется первой. Он открывает ../temp/files.txt в файловом дескрипторе 3 и ../temp/files.txt в файловом дескрипторе 4.
  2. while l oop читает по одной строке из каждого файла и, благодаря &&, останавливается, как только любой файл достигает EOF.
    1. read -u3 source читает из FD 3 в переменную $source.
    2. read -u4 target читает из FD 4 в переменную $target.
    3. IFS= и -r - это очень осторожные опции для отключения всех искажений ввода. В частности, IFS= сообщает read не удалять начальные пробелы, а -r говорит ему оставить в покое обратную косую черту.
  3. Вызов mv каждый раз, когда мы получаем строку из обоих файлов .
1 голос
/ 09 июля 2020

Предполагая, что оба файла имеют одинаковое количество строк (каждая строка представляет имя файла), а имена файлов не содержат символа новой строки или символа табуляции, быстрое bash решение (с использованием paste утилита) может быть:

while IFS=$'\t' read -r from to; do
    echo mv "$from" "$to"
done < <(paste from.txt to.txt)

Удалите echo после тестирования и убедитесь, что он будет работать должным образом.

0 голосов
/ 09 июля 2020

Опять же, нет консоли, но вроде работает

for i in $(seq 1 `wc -l ../temp/files.txt|cut -f 1 -d" "`); do
    mv "`head -n $i ../temp/files.txt|tail -1`" "`head -n $i ../temp/filenames.txt|tail -1`"
done
...