Perl Regex仅输出可用作unix文件名的字符

时间:2010-12-26 02:19:25

标签: regex perl mp3

我为自己写了一个基本的mp3组织脚本。我有一句话:$outname = "/home/jebsky/safehouse/music/mp3/" . $inital . "/" . $artist . "/" . $year ." - ". $album . "/" . $track ." - ". $artist ." - ". $title . ".mp3";

我想要一个正则表达式来更改$outname,以便任何非安全的文件名字符都被下划线替换

2 个答案:

答案 0 :(得分:1)

如果你的任何组件包含“/”,你真的想在将它们组装成$ outname之前对它们进行替换。

哪些字符安全可能因操作系统和/或文件系统而异。 许多文件系统对“/”和nul以外的任何字符都没有问题。由于文件系统允许的其他原因,您最好决定要保留哪些字符。

以下仅保留字母和数字,用_:

替换其他字符的序列
for ( $initial, $artist, $year, $album, $track, $title ) {
    s/[^A-Za-z0-9]+/_/g;
}

答案 1 :(得分:0)

一种快速转义字符串中所有非字母字符的方法是使用\ Q和\ U运算符,如:

# assuming $outname already contains the required path and
# globally "unescaping" file chars / and .

($outname = "\Q$outname\U") =~ s/\\([\/\.])/$1/g;

要考虑的一件事是,像你这样的长期连续猫猫往往难以阅读和维护。表示此操作的更好方法可能是将其分解为逻辑单元,例如:

my $basename   = '/home/jebsky/safehouse/music/mp3';
my $dirpath    = "${basename}/${initial}/${artist}/${year}-${album}/";
my $filename   = "${track}-${artist}-${title}.mp3";

$outname       = "${dirpath}/${filename}";

在字符串中,将变量表示为“$ {varname}”可确保varname后面的字符不会干扰它,即使var之后的下一个字符不是字母数字也是一个好主意,因为它清楚地标记字符串中的变量。

最后,我认为放弃使用'''和'\''作为字符串分隔符是一个好主意,因为如果字符串包含分隔符,它们需要引用。

使用qq //和q //分隔符(如果需要,将/替换为字符串中没有出现的char),如:

my $basename   = q!/home/jebsky/safehouse/music/mp3!;
my $dirpath    = qq!${basename}/${initial}/${artist}!;
my $filename   = qq!${year}-${album}/${track}-${artist}-${title}.mp3!;

$outname       = qq!${dirpath}/${filename}!;

这样,您很少需要引用字符串中的任何字符。