我想在Perl中的目录模式上找到一个文件模式,它将返回数千个条目,如下所示:
find ~/mydir/*/??/???/???? -name "\*.$refinfilebase.search" -print
我被告知有不同的方法来处理它?即:
File::Find
glob()
opendir, readdir, grep
Diamond operator, e.g.: my @files = <$refinfilebase.search>
哪个最适合能够在旧版本的Perl上运行脚本或最小的Perl安装?
答案 0 :(得分:2)
对于非常大的目录,opendir()
可能是最安全的,因为它不需要读取所有内容或对其进行任何过滤。这可能更快,因为排序并不重要,并且在非常大的目录上,在某些操作系统上,这可能会影响性能。 opendir也内置了所有系统。
请注意,它在不同平台上的实际行为方式可能有所不同。所以你需要小心编码。这主要影响它返回的内容,如父目录和当前目录,您可能需要特别处理。
当您只想要一些按模式匹配的文件时, glob()
会更有用。通过一组嵌套目录递归时,File::Find
更有用。如果您不需要,opendir()
是一个很好的基础。
答案 1 :(得分:1)
你也有DirHandle
DIRHANDLE:
use DirHandle;
$d = new DirHandle ".";
if (defined $d) {
while (defined($_ = $d->read)) { something($_); }
$d->rewind;
while (defined($_ = $d->read)) { something_else($_); }
undef $d;
}
对于readdir和glob的用例,请参阅 What reasons are there to prefer glob over readdir (or vice-versa) in Perl?
我更喜欢使用glob
快速获取目录中的文件列表(无子目录)并像处理
map {process_bam($ _)} glob(bam_files / * .bam)
这样更方便,因为它不需要。并且..如果你在glob模式中使用dir,你甚至要求(*)并返回完整路径。
当你需要预处理列表的文件名时,你可以快速使用glob作为oneliner管道传输到xargs或bash for循环:
perl -lE 'print join("\n", map {s/srf\/(.+).srf/$1/;$_} glob("srf/198*.srf"))' | xargs -n 1.....
Readdir在其他情况下有冒险,因此您需要使用更适合您行为的那个。