Regex 填充数百个文件中第二次出现的数字
我有数百个文件使用以下方案命名: XX-YY Title.ext 但是,它们并不总是正确排序,因为XX和YY可以是1或2位数字。我想重命名文件,以便XX和YY始终是2位数字,如果需要,可以添加前导零 例如,我目前得到的排序如下所示:Regex 填充数百个文件中第二次出现的数字,regex,perl,Regex,Perl,我有数百个文件使用以下方案命名: XX-YY Title.ext 但是,它们并不总是正确排序,因为XX和YY可以是1或2位数字。我想重命名文件,以便XX和YY始终是2位数字,如果需要,可以添加前导零 例如,我目前得到的排序如下所示: 1 - 1 BillyBob.ext 1 - 10 Jimmy2.ext 1 - 2 Stewy3.ext 10 - 1 Cletus.ext 2 - 1 Homer.ext s/(\d+) - (\d+)/sprintf('%02d -
1 - 1 BillyBob.ext
1 - 10 Jimmy2.ext
1 - 2 Stewy3.ext
10 - 1 Cletus.ext
2 - 1 Homer.ext
s/(\d+) - (\d+)/sprintf('%02d - %02d', $1, $2)/e;
我想要的是:
01 - 01 BillyBob.ext
01 - 02 Stewy3.ext
01 - 10 Jimmy2.ext
02 - 01 Homer.ext
10 - 01 Cletus.ext
我已使用以下代码成功更改XX部件:
rename -n 's/\d+/sprintf("%02d", $&)/e' *
然而,我似乎不知道如何执行将对YY部分起作用的东西
****附于原职位****
更具体地说,我不知道如何处理YY部分,而不处理文件名后面出现的任何数字特许
****结束附加内容****
感谢您的帮助
谢谢 替换运算符上缺少/g。如果没有它,Perl只会更改字符串中的第一个正则表达式匹配项
#!/usr/bin/perl
use strict;
use warnings;
while (<DATA>) {
s/\d+/sprintf('%02d', $&)/eg;
print;
}
__DATA__
1 - 1 BillyBob.ext
1 - 10 Jimmy.ext
1 - 2 Stewy.ext
10 - 1 Cletus.ext
2 - 1 Homer.ext
更新:为了处理您添加到问题中的新要求,我们需要使正则表达式更加明确。在这个修复中,我要寻找两组由破折号分隔的数字。我捕获两组数字,将它们放在$1和$2中,并在替换运算符的右侧展开它们
我唯一需要更改的行是包含替换的行。现在看起来是这样的:
1 - 1 BillyBob.ext
1 - 10 Jimmy2.ext
1 - 2 Stewy3.ext
10 - 1 Cletus.ext
2 - 1 Homer.ext
s/(\d+) - (\d+)/sprintf('%02d - %02d', $1, $2)/e;
而且,由于我们在这里只进行一次替换,因此可能会丢失/g选项。您的替换运算符缺少/g。如果没有它,Perl只会更改字符串中的第一个正则表达式匹配项
#!/usr/bin/perl
use strict;
use warnings;
while (<DATA>) {
s/\d+/sprintf('%02d', $&)/eg;
print;
}
__DATA__
1 - 1 BillyBob.ext
1 - 10 Jimmy.ext
1 - 2 Stewy.ext
10 - 1 Cletus.ext
2 - 1 Homer.ext
更新:为了处理您添加到问题中的新要求,我们需要使正则表达式更加明确。在这个修复中,我要寻找两组由破折号分隔的数字。我捕获两组数字,将它们放在$1和$2中,并在替换运算符的右侧展开它们
我唯一需要更改的行是包含替换的行。现在看起来是这样的:
1 - 1 BillyBob.ext
1 - 10 Jimmy2.ext
1 - 2 Stewy3.ext
10 - 1 Cletus.ext
2 - 1 Homer.ext
s/(\d+) - (\d+)/sprintf('%02d - %02d', $1, $2)/e;
而且,由于我们在这里只进行了一次替换,我们可能会丢失/g选项。为了完整性:这也可以通过GNU coreutils的排序直接在UNIX shell上解决: $cat dummy.txt 1-1 BillyBob.ext 1-10吉米分机 1-2 Stewy.ext 10-1 Cletus.ext 2-1 Homer.ext
$sort-field separator=--k 1n-k 2n完整性:这也可以在UNIX shell上通过GNU coreutils的排序直接解决: $cat dummy.txt 1-1 BillyBob.ext 1-10吉米分机 1-2 Stewy.ext 10-1 Cletus.ext 2-1 Homer.ext
$sort-fieldseparator=-k1n-k2n试试这个Perl一行程序
perl -lne ' s/(\d+)\s-\s(\d+)\s+(\S+)/sprintf("%02d-%02d %s",$1,$2,$3)/ge; $kv{$_}=1 ; END { print join("\n",sort keys %kv) } '
有投入
$ cat notorious.txt
1 - 1 BillyBob.ext
1 - 10 Jimmy.ext
1 - 2 Stewy.ext
10 - 1 Cletus.ext
2 - 1 Homer.ext
$ perl -lne ' s/(\d+)\s-\s(\d+)\s+(\S+)/sprintf("%02d-%02d %s",$1,$2,$3)/ge; $kv{$_}=1 ; END { print join("\n",sort keys %kv) } ' notorious.txt
01-01 BillyBob.ext
01-02 Stewy.ext
01-10 Jimmy.ext
02-01 Homer.ext
10-01 Cletus.ext
$
试试这个Perl单行程序
perl -lne ' s/(\d+)\s-\s(\d+)\s+(\S+)/sprintf("%02d-%02d %s",$1,$2,$3)/ge; $kv{$_}=1 ; END { print join("\n",sort keys %kv) } '
有投入
$ cat notorious.txt
1 - 1 BillyBob.ext
1 - 10 Jimmy.ext
1 - 2 Stewy.ext
10 - 1 Cletus.ext
2 - 1 Homer.ext
$ perl -lne ' s/(\d+)\s-\s(\d+)\s+(\S+)/sprintf("%02d-%02d %s",$1,$2,$3)/ge; $kv{$_}=1 ; END { print join("\n",sort keys %kv) } ' notorious.txt
01-01 BillyBob.ext
01-02 Stewy.ext
01-10 Jimmy.ext
02-01 Homer.ext
10-01 Cletus.ext
$
隐马尔可夫模型。。。Windows的资源管理器“我的电脑”实际上是按照您想要的顺序对这些名称进行排序的,那么,有什么不对您进行正确排序呢?如果您指的是Perl的排序,那么只需使用sort::Key::Natural的natsort而不是内置排序。嗯。。。Windows的资源管理器“我的电脑”实际上是按照您想要的顺序对这些名称进行排序的,那么,有什么不对您进行正确排序呢?如果您指的是Perl的排序,那么只需使用sort::Key::Natural的natsort而不是内置排序即可expected@stack0114106:OP要求重命名文件。他知道如何对结果进行排序。很好的呼叫全球操作员。然而,我在最初的帖子中没有提到的是,我的文件名中的一些名称也包含数字字符。如果我对它进行全局处理,它将使排序工作正常。但是,任何其他数字字符也会被删除。我已经更新了原始帖子,以反映以前未说明的情况。输出未按OP排序expected@stack0114106:OP要求重命名文件。他知道如何对结果进行排序。很好的呼叫全球操作员。然而,我在最初的帖子中没有提到的是,我的文件名中的一些名称也包含数字字符。如果我对它进行全局处理,它将使排序工作正常。但是,任何其他数字字符也会被删除。我已经更新了原始帖子,以反映这种以前未说明的情况。