2013-02-15 3 views
2

Я только что загрузил около 600 файлов с моего сервера и вам нужно удалить последние 11 символов из имени файла (не включая расширение). Я использую Ubuntu, и я ищу команду для достижения этой цели.Удаление 10 символов имени файла в Linux

Некоторые примеры являются следующие:

aarondyne_kh2_13thstruggle_or_1250556383.mus должен быть переименован в aarondyne_kh2_13thstruggle_or.mus

aarondyne_kh2_darknessofunknow_1250556659.mp3 должен быть переименован в aarondyne_kh2_darknessofunknow.mp3

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

ответ

3

Попробуйте использовать команду rename. Это позволяет переименовывать файлы на основе регулярного выражения:

Следующая строка должна работать для вас:

rename 's/_\d+(\.[a-z0-9A-Z]+)$/$1/' * 

следующие изменения будут происходить:

aarondyne_kh2_13thstruggle_or_1250556383.mus renamed as aarondyne_kh2_13thstruggle_or.mus 
aarondyne_kh2_darknessofunknow_1250556659.mp3 renamed as aarondyne_kh2_darknessofunknow.mp3 

Вы можете проверить действия rename будет делать с помощью указания -n флага, как это:

rename -n 's/_\d+(\.[a-z0-9A-Z]+)$/$1/' * 

Для получения дополнительной информации о том, как использовать rename просто открыть справочную страницу через: man rename

+4

Внимание: моя версия переименования (фондовая федерация 18!) Не имеет флага '' -n'' и работает вообще в целом. В частности, он не поддерживает регулярные выражения, а только глобусы. –

+0

@JonasWielicki Спасибо за примечание. Я протестировал ответ на мой Ubuntu 12.10 Desktop, поэтому он должен поработать для первоначального вопроса, по крайней мере. – TimWolla

+1

Спасибо вам большое. Это помогло мне! –

1

Не самый красивый, но очень просто:

echo "$filename" | sed -e 's!\(.*\)...........\(\.[^.]*\)!\1\2!' 

Вам все еще нужно, чтобы написать остальную часть сценария, но это довольно просто.

+0

Интересно. Я знаю, например. 'sed -e s/anton/berta' заменить' anton' на 'berta', используя' s' для 'substitute'.Ваш синтаксис пропускает косые черты! И что такое '[^.]' Для? Это исключает все символы ?. Я знаю 'man sed' .. – Timo

+0

ohh,'! 'Теперь является разделителем, потому что он лучше для имен файлов, поэтому вы ищете' ... 'и не заменяете его ничем (' \ 1 \ 2')? – Timo

+0

плюс один для простого дизайна. Как вы знаете, чтобы начать с конца без расширения? – Timo

0

один способ пойти:

вы получите список файлов, по одному в каждой строке (по ls, может быть), то:

ls....|awk '{o=$0;sub(/_[^_.]*\./,".",$0);print "mv "o" "$0}' 

отпечатывается команду mv a b

например

kent$ echo "aarondyne_kh2_13thstruggle_or_1250556383.mus"|awk '{o=$0;sub(/_[^_.]*\./,".",$0);print "mv "o" "$0}' 
mv aarondyne_kh2_13thstruggle_or_1250556383.mus aarondyne_kh2_13thstruggle_or.mus 

выполнить, только через канал, |sh

Я полагаю, что нет места в вашем имени.

+1

. Существуют более безопасные способы получения имен всех файлов, чем разбор выходных данных 'ls'; см. http://mywiki.wooledge.org/ParsingLs – chepner

1
find . -type f -exec sh -c 'mv {} `echo -n {} | sed -E -e "s/[^/]{10}(\\.[^\\.]+)?$/\\1/"`' ";" 
+0

Мне нравится короткий синтаксис, поэтому плюс 1. Можете ли вы объяснить, что вы сделали? Вы заменили всех персонажей, но не. ('[^ \\.]') без ничего ('\\ 1')? Как sed знает, чтобы начать с конца, но исключая расширение? – Timo

0

Этот скрипт предполагает, что каждый файл имеет только одно расширение. Например, он переименовал бы «foo.something.mus» в «foo.mus». Чтобы сохранить все расширения, удалите одну метку хэша (#) из первой строки тела цикла. Он также предполагает, что база каждого имени файла имеет не менее 12 символов, так что удаление 11 не оставляет вас с пустым именем.

for f in *; do 
    ext=${f##*.} 
    new_f=${base%???????????.$ext} 
    if [ -f "$new_f" ]; then 
     echo "Will not rename $f, $new_f already exists" >&2 
    else 
     mv "$f" "$new_f" 
    fi 
done 
Смежные вопросы