我正在尝试编写一个脚本,从脚本所在的文件夹开始打印出文件结构.脚本工作正常,没有递归调用但是通过该调用它打印第一个文件夹的内容并崩溃并显示以下消息:closedir()尝试在printFiles.pl第24行无效的dirhandle DIR.文件夹被打印,执行到达最后一行,但为什么不进行递归调用?我应该如何解决这个问题呢?
#!/usr/bin/perl -w
printDir(".");
sub printDir{
opendir(DIR, $_[0]);
local(@files);
local(@dirs);
(@files) = readdir(DIR);
foreach $file (@files) {
if (-f $file) {
print $file . "\n";
}
if (-d $file && $file ne "." && $file ne "..") {
push(@dirs, $file);
}
}
foreach $dir (@dirs) {
print "\n";
print $dir . "\n";
printDir($dir);
}
closedir(DIR);
}
Run Code Online (Sandbox Code Playgroud)
你应该始终use strict;并use warnings;在Perl程序开始时,特别是在你寻求帮助之前.这样Perl会出现很多直截了当的错误,否则你可能没有注意到.
该无效文件句柄错误可能是因为DIR是一个全球性的目录句柄,并已通过子程序的先前执行已经关闭.最好始终为文件和目录使用词法句柄,并测试返回代码以确保打开成功,如下所示
opendir my $dh, $_[0] or die "Failed to open $_[0]: $!";
Run Code Online (Sandbox Code Playgroud)
词法文件句柄的一个优点是它们在超出范围时会隐式关闭,因此closedir在子例程结束时不需要调用.
local并不意味着像这样使用.它不足以作为声明,并且您正在创建一切可以访问的全局变量的临时副本.最好使用my,就像这样
my @dirs;
my @files = readdir $dh;
Run Code Online (Sandbox Code Playgroud)此外,您是从使用的文件名readdir没有路径,所以,除非您或者您的文件测试将无法chdir在目录中被处理或测试之前,追加的目录路径字符串的文件名.