Яка різниця між 'перейменувати' та 'mv'?


12

Мені це не зовсім зрозуміло, але в чому різниця між mvі rename(від util-linux-ng 2.17.2як /usr/bin/rename)? Чи є переваги одного над іншим, крім renameприйняття регулярних виразів, а mvні? Я вважаю, що renameтакож можна обробити кілька перейменів файлів одночасно, тоді як mvце не робиться.

Я не міг знайти чітких вказівок на їхніх manсторінках, що ще їх вирізняє, або я провів самостійне дослідження.


2
Давайте переконаємось, що ми говоримо про одні і ті ж речі; з яких результатів type -a renameі rename --version?
Jeff Schaller

@JeffSchaller Це більше цікавості з мого боку, але на одному з моїх * NIX машин я отримую rename is /usr/bin/renameі rename (util-linux-ng 2.17.2)відповідно.
Урда

6
Там є кілька різних перейменувань , і це могло бути псевдонім / функція / сценарій, тому я просто хотів переконатися, що ми знаємо, що це. Дякую! Будь ласка, відредагуйте ці результати у своєму запитанні.
Джефф Шаллер

@JeffSchaller не хвилюйтесь, насправді саме це посилання було одним, що я щойно знайшов, що показав, що renameможе означати різні речі в різних дистрибутивах.
Урда

5
Схоже, ваше запитання містить свою відповідь. "Яка різниця між струменем і трициклом, крім того, що реактивний літак може літати і може пройти в кілька тисяч разів швидше?" :-) ⁠
G-Man каже: "Відновіть Моніку"

Відповіді:


21

Це в основному те, що написано на кришці, для обох.

mv- це стандартна утиліта для переміщення одного або декількох файлів до заданої цілі. Його можна використовувати для перейменування файлу, якщо для переміщення є лише один файл. Якщо їх декілька, mvпрацює лише, якщо цільовим є каталог, і переміщує файли туди.

Так mv foo barбуде або перемістити файл fooу каталог bar(якщо він існує), або перейменувати fooв bar(якщо barйого немає або немає каталогу). mv foo1 foo2 barпросто перемістить обидва файли в каталог bar, або скаржиться, якщо barце не каталог.

mvвикличе rename()функцію бібліотеки С для переміщення файлів, і якщо це не працює (вони переміщуються в іншу файлову систему), він скопіює файли та видалить оригінали.

Якщо все, що у вас є, mvі ви хочете перейменувати кілька файлів, вам доведеться скористатися циклом оболонки. Є цілий ряд питань про те , що тут на сайті, дивіться , наприклад , це , це , і інші .


З іншого боку, різні renameутиліти перейменують файли окремо.

renameВід Util-Linux , який ви згадуєте робить просту рядок заміни, наприклад , rename foo bar *зміниться foobarна barbar, і asdffooна asdfbar. Однак це не приймає регулярного виразу!

Утиліта перейменування Perl ( або різні її примірники ) використовує вираз Perl для перетворення імен файлів. Можна, швидше за все, використовувати команду, де шаблон є регулярним виразом.s/pattern/replacement/

Як перейменування util-linux, так і перейменування Perl можна одночасно використовувати для переміщення файлів до іншого каталогу, вносячи відповідні зміни до імені файлу, але це трохи незручно. Також rename()файли не викликають більше , тому переміщення з однієї файлової системи в іншу не працює.

Що стосується того, що у renameвас є, це може залежати від вашого розповсюдження та / або того, що ви встановили. Більшість з них підтримують rename --version, тому використовуйте це, щоб визначити, який у вас є.


Не тільки «регулярний вираз», але і функціонувати, якщо це потрібно
Жилль Квінот

@GillesQuenot, так, так, можна зробити, наприклад, rename '$_=lc' *для малих імен файлів. Але я думаю, що найпоширеніший випадок - це використання s///(про яке я згадував), а частина його шаблону - це регулярний вираз; Я не думаю, що ти можеш використовувати там функцію. Ви можете зробити це в замінній частині.
ilkkachu

@MyWrathAcademia, перший приклад на сторінці man працює для мене (він просто робить інакше, ніж інший). Крім того, причина, по якій я пов’язана з Debian-маніпуляціями, полягає в тому, що принаймні там стало зрозуміло, що сторінка man для rename.ulі є для версії util-linux, а не для будь-якої іншої.
ilkkachu

@ilkkachu, чи не проти додати пояснення до цього першого прикладу або у відповідь, або в коментар. Він відрізняється від прикладу man renameтим, що було б добре знати ваше розуміння прикладу debian
MyWrathAcademia

@MyWrathAcademia, я припускав, що ти маєш на увазі rename foo foo0 foo?; rename foo foo0 foo??приклад, оскільки це була єдина різниця між цими двома сторінками, які я бачив. Ця пара команд працює, тому що перша додає нуль до імен кожного одноцифрового імені файлу, а після цього друга додає (інший) нуль кожному двозначному імені файлу. Цей другий набір включає файли, перейменовані першою командою. Використовуючи rename foo foo00 foo?як першу команду також працює, вона просто додає дві нулі за один раз.
ilkkachu

2

mvпросто змінює ім'я файлу (він також може перемістити його в іншу файлову систему або шлях). Ви даєте йому старе ім’я та нове ім'я, і ​​воно змінює файл на нове ім'я чи місце розташування. renameвикористовується для внесення масових змін в іменування. Скажіть, у вас було тисячу файлів foo000.logнаскрізь, foo999.logі ви хотіли змінити їх на bar000.logнаскрізний bar999.log. З mvвами доведеться робити mv foo000.log bar000.log, mv foo001 bar001.logі т.д., або ще написати сценарій. З renameвами просто rename foo bar foo*.log, і вуаля, тисяча файлів змінюється за мить! Дуже здорово. Перегляньте man renameсторінку ще раз, щоб отримати детальну інформацію.


2

mv

Це основний командний рядок, розроблений для того, щоб робити одне і робити це добре (філософія Unix): переміщення файлів (ів) або дирекцій (и) .

Ви можете зламати STDOUT& STDIN¹, щоб змінити на ходу рядок призначення, але це просто не розумний злом

перейменувати (Perl's)

увага Є й інші інструменти з такою ж назвою, які можуть чи не можуть це зробити, тому будьте уважні.

Коли люди говорять про renameнас, ми думаємо про це, а не про ELFодне, менш потужне (магія?).

Це не є основним, це Perl. Ви можете передавати деякі функції Perl всередині, і це надзвичайно потужно.

Розглянемо цей приклад:

Ви хочете перейменувати купу файлів типу

foobar_1.txt
foobar_2.txt
foobar_3.txt

Ви можете додати нулі до цифр sprintf()таким чином (використовуючи регулярний вираз, хе, це Perl: D):

rename 's/(\d+)/sprintf("%04d", $1)/e' foobar_*.txt

Тепер у вас є:

foobar_0001.txt
foobar_0002.txt
foobar_0003.txt

Насправді не основна команда, чи не так?

насправді не розроблено для переміщення режимів , але це можна зробити:

$ mkdir -p /tmp/foo/bar/base
$ touch /tmp/foo/bar/base/file
$ rename 's!/tmp/foo/bar/base/file!/tmp/file!' /tmp/foo/bar/base/file

Переміщений файл

/tmp/file

¹ якийсь код, який ми бачимо на *.stackexchange.*веб-сайтах

введіть тут опис зображення

for FILE in `ls *.txt`
do
    mv ${FILE} `echo ${FILE} | sed 's/anything_ugly/anything_still_ugly/'`
done

Це не шлях , це звичайний баггі, просто пояснити, навіщо користуватися правильним інструментом в потрібний момент


+1 для sprintfінн з перейменуванням
Archemar

-1

mv переміщує або перейменовує файли та каталоги та створює резервну копію; перейменувати просто перейменувати файли.

mv має більше можливостей та можливостей. Подивіться на перемикачі на сторінках man для кожної, щоб побачити відмінності у можливостях. Давайте подивимось, використовуючи man в Ubuntu 18.04LTS (ваш пробіг може змінюватися в залежності від версії кожного пакета):

опції mv (опускаючи довідку та версію)

   --backup[=CONTROL]  
          make a backup of each existing destination file  

   -b     like --backup but does not accept an argument  

   -f, --force  
          do not prompt before overwriting  

   -i, --interactive  
          prompt before overwrite  

   -n, --no-clobber  
          do not overwrite an existing file  

  If you specify more than one of -i, -f, -n, only the final one takes effect.  

   --strip-trailing-slashes  
          remove any trailing slashes from each SOURCE argument  

   -S, --suffix=SUFFIX  
          override the usual backup suffix  

   -t, --target-directory=DIRECTORY  
          move all SOURCE arguments into DIRECTORY  

   -T, --no-target-directory  
          treat DEST as a normal file  

   -u, --update  
          move only when the SOURCE file is newer than the destination file or when the destination file is missing  

   -v, --verbose  
          explain what is being done  

   -Z, --context  
          set SELinux security context of destination file to default type  

перейменувати параметри (опускаючи довідку та версію)

   -s, --symlink   
          Do not rename a symlink but its target.  

   -v, --verbose  
          Show which files where renamed, if any.  

   -n, --no-act  
          Do not make any changes.  

   -o, --no-overwrite  
          Do not overwrite existing files.            

3
Визначте "потужніший". Чи підтримує mv регулярний вираз, як перейменувати?
Жиль Кінот

Як заявив запитуючий, ні.
K7AAY

2
Нічого собі, який аргумент
Гілль Кінот

1
Надання кредиту, коли належить отримати кредит.
K7AAY
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.