这将重命名所有扩展名为 jpg 的文件。
rename 'y/a-z/A-Z/' *.jpg
这将重命名该文件,但也会重命名扩展名。
rename 'y/a-z/A-Z/' image.jpg
如何在不改变扩展名的情况下重命名单个文件?
example.jpg
输出应该是:
EXAMPLE.jpg
答案1
和改名
rename -n 's/.*\./\U$&/'
-n
争论是为了不做出改变并告诉你将会发生什么。.*
正则表达式世界中的参数是 select一切,与 一起使用\.
是选择点之前的所有内容[.] ⇾.*\.
选择点之前的所有内容。- 使用
\
[反斜杠] 转义字符,因为.
[点] 在正则表达式。
- 使用
\U
argument 表示大写直到,这是一个转义序列在Perl正则表达式中,它必须与\
[反斜杠]一起使用$&
参数用于查找上次成功模式搜索中匹配的字符串。示例/find/$&ADD/
返回:findADD
返回:
rename(fellowSHIP.jpg, FELLOWSHIP.jpg)
rename(retorno2.jpg, RETORNO2.jpg)
rename(retorno3.jpg, RETORNO3.jpg)
rename(retorno4.jpg, RETORNO4.jpg)
rename(shein1.jpg, SHEIN1.jpg)
rename(shein2.jpg, SHEIN2.jpg)
rename(shein3.jpg, SHEIN3.jpg)
rename(shein4.jpg, SHEIN4.jpg)
rename(shein-girl1.jpg, SHEIN-GIRL1.jpg)
rename(sheingirl2.jpg, SHEINGIRL2.jpg)
rename(twoTowers1.jpg, TWOTOWERS1.jpg)
rename(twoTowers2.jpg, TWOTOWERS2.jpg)
rename(twoTowers3.jpg, TWOTOWERS3.jpg)
rename(twoTowers4.jpg, TWOTOWERS4.jpg)
rename(twoTowers5.jpg, TWOTOWERS5.jpg)
rename(twoTowers6.jpg, TWOTOWERS6.jpg)
答案2
rename 's/(.*)(\.[^.]+)/\U$1\E$2/' example.jpg
s/
开始替换(.*)
匹配后缀之前的文件名部分(任何字符,任何数量),在第一组中捕获(\.[^.]+)
匹配后缀,a.
后跟一个或多个非.
字符,在第二组中捕获/
开始更换\U
大写(直到\E
)$1
插入第一个匹配组\E
最终情况修改$2
插入第二个匹配组/
末端替换
答案3
请注意(除了 中不相关且非常有限的一个util-linux
)现在有一些 perlrename
命令的变体(最初是perl
3.0附带的一个非常短的示例脚本)。
与来自https://metacpan.org/dist/File-Rename并在最近基于 Debian 的系统上的软件包中找到rename
,要将任意文件名中的所有 ASCII 字母转为大写,但扩展名中不转为大写(如果有),您可以执行以下操作:
rename -d -- 's/.*\.|.*/\U$&/s' "$file"
在哪里:
-d
确保文件的目录名不受影响。--
该实现需要,否则将采用$file
开头-
作为选项(--e=exec("rm -rf ~")
例如,对于调用的文件会产生灾难性的后果)。- 需要 ubstitute
s
的标志,否则将不会匹配换行符(与文件名中的任何字符一样有效的字符)。s
.
.*\.|.*
匹配最右边的任何内容.
(如.*
贪婪)或所有内容,请记住,perl
首先尝试左侧模式并且与 POSIX 正则表达式相反,不会尝试查看另一个模式是否会产生更长的匹配。因此,对于有扩展名的文件,它将匹配扩展名之前的内容;对于没有扩展名的文件,它将匹配整个文件名。$&
是匹配的内容。以 为前缀\U
,会被转换为大写,就像在ex
/vi
中perl
借用的一样。
示例-n
(用于试运行):
$ rename -n -d -- 's/.*\.|.*/\U$&/s' $'--e=system("echo reboot") #/foo\nbar.jpg'
rename(--e=system("echo reboot") #/foo
bar.jpg, --e=system("echo reboot") #/FOO
BAR.jpg)
$ rename -n -d -- 's/.*\.|.*/\U$&/s' .config/gtkrc
rename(.config/gtkrc, .config/GTKRC)
$ rename -n -d -- 's/.*\.|.*/\U$&/s' .bashrc
$
(在.bashrc
这里,bashrc
被视为扩展)。
现在,一个问题是它仅适用于 ASCII 文件名。
例如,它会将 UTF-8 转换Stéphane.jpg
为STéPHANE.jpg
而不是STÉPHANE.jpg
(至少é
在预组合形式的情况下)或更糟糕地将 BIG5-HKSCS 转换Stéphane.jpg
为St<U+F310>phane.jpg
.
解决这个问题rename
有点痛苦。你需要类似的东西:
rename -n -d -- '
use Encode::Locale;
use Encode;
$_ = decode(locale_fs => $_);
s/.*\.|.*/\U$&/s;
$_ = encode(locale_fs => $_)' "$file"
将文件视为使用区域设置的字符集进行编码。
但请注意,它会将无法解码为字符的字节转换为某些替换字符(类似于?
或�
取决于语言环境;在 C 语言环境中,包括高于 127 的所有字节值)。
最后,使用 shell 的操作符可能会更容易、更安全。像zsh
:
case $file:t in
(*.*) newfile=$file:h/$file:t:r:u.$file:e;;
(*) newfile=$file:h/$file:t:u;;
esac
[[ $file = $newfile ]] || mv -i -- $file $newfile
(其中:t
、:h
、:r
、:e
、:u
是 csh 风格的修饰符,分别产生t
ail、h
ead、r
ootname、e
xtension 和 Turn 为u
ppercase)。
zsh
的运算符将尽最大努力:转换可以解码的字符,而保留无法解码的字节序列。
zsh
还有它自己的内置批量重命名工具:zmv
,作为自动加载函数实现:
autoload -Uz zmv # best in ~/.zshrc
zmv '(*).(*)' '$1:u.$2'
(仅重命名具有扩展名的非隐藏文件)
zmv
在开始重命名之前还会进行一些健全性检查,这也使其比rename
.