Рекурсивно переименовывать файлы, сохраняя при этом все символы, предшествующие подчеркиванию

Чтобы ответить на ваш вопрос:

fgrep -w -f genelist.txt data.txt >results.txt
  • fgrep ищет фиксированные строки, а не регулярные выражения (как grep и egrep )
  • -w сообщает fgrep соответствие целым словам, поэтому ABC123 не будет соответствовать ABC1234
  • -f genelist.txt сообщает fgrep для чтения шаблонов поиска из genelist.txt .

Узнать, какие гены из genelist.txt не были включены в извлечение, немного сложнее. Один из способов сделать это:

awk '{ print $1 }' results.txt | fgrep -w -v -f - genelist.txt >outsiders.txt
  • awk '{print $ 1}' печатает первый столбец в текстовом файле; это список сопоставленных генов
  • fgrep снова соответствует фиксированным строкам
  • -w указывает fgrep сопоставить целые слова
  • -v указывает ему печатать строки, которые не соответствуют
  • -f - , указывают ему прочитать список шаблонов из stdin , то есть список совпадающих генов из awk .

Вы также можете сделать вещи немного более эффективными, удалив дубликаты из списка совпадающих генов перед поиском, вставив sort -u между awk и fgrep ]:

awk '{ print $1 }' results.txt | sort -u | fgrep -w -v -f - genelist.txt >outsiders.txt
3
20.12.2016, 03:32
3 ответа

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

find /home/scott/ -maxdepth 4 -type f -name '*_*.wav' -exec sh -c 'h=${1%/*}
t=${1##*/}; echo mv "$1" "${h}/${t%%_*}".wav' doom {} \;

удалите echo , чтобы фактически переименовать файлы.

2
27.01.2020, 21:18

Я много искал и видел много способов изменить другие части имени файла, но не сохранить все до определенного { {1}} символ (_) и расширение.

Этот sed , похоже, помогает: sed -E 's / (. *) _ [0-9]. * By. * (\. Wav ) / \ 1 \ 2 / '

echo "/home/user/recordings/TEST/december/157A757989F047C3AC2EC3499B4D04A5_7075276189 by user@domain.com @ 8_44_52 AM.wav" | sed -E 's/(.*)_[0-9].* by .*(\.wav)/\1\2/'
/home/user/recordings/TEST/december/157A757989F047C3AC2EC3499B4D04A5.wav

Тестирование на другом примере строки:

echo "/home/user/recordings/test/october/28D1E1840DE24D9DB4CF6D1A707533F6337C2DDE_2018690759 by user@domain.com @ 1_26_55 PM.wav" | sed -E 's/(.*)_[0-9].* by .*(\.wav)/\1\2/'
/home/user/recordings/test/october/28D1E1840DE24D9DB4CF6D1A707533F6337C2DDE.wav

С помощью sed вы сохраняете части своего выражения с помощью () , а затем помещаете их обратно с \ 1 \ 2 .

1
27.01.2020, 21:18

Установите любую из реализаций prename (переименование Perl), например File :: Rename или вариант из Unicode :: Драка . (Последний раз я смотрел, CentOS не поставлялся с переименованием Perl, только с util-linux rename , который не может делать то, что вам нужно, но это могло измениться в CentOS 7.) Все они. имеют базовый синтаксис prename CODE FILENAME ... где CODE - это некоторый код Perl, который применяется для преобразования каждого имени файла.

find /home/user/recordings/ -type f -exec prename 's!_[^/]*(\.[^./]*)$!$1!' {} +

Объяснение для Perl: (\. [^. /] *) $ соответствует расширению в конце имени; _ [^ /] * соответствует всему в имени файла без части каталога (без косой черты), начиная с первого символа подчеркивания. Замена - $ , то есть часть в первой и единственной группе в скобках.

1
27.01.2020, 21:18

Теги

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