写了一个脚本可以同时检查多个仿真log文件,并生成html表格。按照文件修改时间从新到旧排序。然后一直无法使用stath函数获取ctime。
结论:find函数会改变程序执行的当前目录,find(\&process_files, $dir);
函数是在$dir目录下运行的。
测试环境的目录结构如下:
.
├── check_logs.pl
└── logs
├── 1.txt
├── 2.txt
└── 3.txt
1 directory, 4 files
perl提供一个内置函数stat()获取文件相关信息,函数返回一个数组。
官方文档介绍stat - Perldoc 浏览器
my($dev, $ino, $mode, $nlink, $uid, $gid, $rdev, $size, $atime, $mtime, $ctime, $blksize, $blocks) = stat($file_name);
介绍几个比较重要的含义:
先看下使用内置函数获取修改时间的代码
#! /bin/perl -w
use strict;
use warnings;
use File::Find;
use File::Basename;
my $time = (stat("./logs/1.txt"))[10];
print "$time\n";
运行结果如下:
[fengbh@VM-16-14-centos perl_stat]$ ./check_logs.pl
1703579691
File::stat会覆盖内置的系统函数,它以类的方式提供类似内置函数stat的功能。
官方文档File::stat - by-name interface to Perl’s built-in stat() functions - Perldoc Browser
使用类的方式获取修改时间的代码如下:
#! /bin/perl -w
use strict;
use warnings;
use File::Find;
use File::stat;
my $time = stat("./logs/1.txt")->mtime;
print "$time\n";
运行结果如下:
[fengbh@VM-16-14-centos perl_stat]$ ./check_logs.pl
1703579691
这里使用内置函数的方式实现。
#! /bin/perl -w
use strict;
use warnings;
use File::Find;
my $dir = "./logs";
find(\&process_files, $dir);
sub process_files{
return if !-f $_;
#debug
print "\$_ = $_\n";
print "\$File::Find::name = $File::Find::name\n\n";
#get mtime
my $mtime = (stat($File::Find::name))[10];
die "Can't stat file;$!\n" if !defined($mtime);
# debug
print "mtime = $mtime\n";
}
运行结果:
[fengbh@VM-16-14-centos perl_stat]$ ./check_logs.pl
$_ = 3.txt
$File::Find::name = ./logs/3.txt
Can't stat file;No such file or directory
运行发现报错,找不到文件。但是传给stat函数的文件路径名是正确的。
这是因为find函数会改变程序执行的当前目录,或者可以理解为process_files函数是在$dir目录下运行的。
这就是报错的原因,$File::Find::name是相对于初始执行目录的路径,$_才是相对于$dir的路径。
将代码修改为:
#! /bin/perl -w
use strict;
use warnings;
use File::Find;
my $dir = "./logs";
find(\&process_files, $dir);
sub process_files{
return if !-f $_;
#debug
print "\$_ = $_\n";
print "\$File::Find::name = $File::Find::name\n\n";
#get mtime
my $mtime = (stat($_))[10];
die "Can't stat file;$!\n" if !defined($mtime);
# debug
print "mtime = $mtime\n";
}
执行结果如下:
[fengbh@VM-16-14-centos perl_stat]$ ./check_logs.pl
$_ = 3.txt
$File::Find::name = ./logs/3.txt
mtime = 1703577429
$_ = 1.txt
$File::Find::name = ./logs/1.txt
mtime = 1703579691
$_ = 2.txt
$File::Find::name = ./logs/2.txt
mtime = 1703577426
执行结果正确