Perl 文件操作
Perl 对文件和目录操作提供了相关的增删改查API, 如rename, rmdir, unlink 等函数, 但是笔者认为并没有太大必要去花时间掌握这些函数, 因为perl 通过system 函数可以直接执行系统命令, 所以直接使用system+原生linux文件操作命令即可, 这样可以少学一套API. 因此, 笔者更常用于此种方式.
1. 文件内容读写
1.1 文件句柄
- perl 程序通过文件句柄和文件进行文件读写
- 文件句柄: 文件句柄相当于一个指针, 指向这个文件; 句柄必须是全部大写或者为标量, 笔者建议句柄会用标量, 因为perl默认的文件句柄为全部大写.
- perl 内置句柄有: STDIN, STDOUT, STDERROR 等
- perl 文件打开后未关闭的话, 在程序借宿时会自动关闭
1.1.1 打开文件句柄
- 语法: open 句柄名称, 打开方式, 文件名;
常用打开方式:
打开方式 |
含义 |
< |
以输入方式打开文件, 用于读取文件内容 |
> |
以输出方式打开文件, 用于写文件, 打开的同时会清空文件内容 |
>> |
以输出方式打开文件, 用于写文件, 打开时不清空文件, 直接在文件末尾追加内容 |
>:encoding(UTF-8) |
以指定编码打开文件, 可用于以上三种方式 |
1.1.2 关闭文件句柄
- 语法: close 文件句柄名称;
- 当文件不使用的时候建议关闭文件句柄, 减少资源占用.若不手动关闭的话, 当程序结束时, 会自动关闭.
1.2 读文件
- 当文件比较小的时候, 一次性读取文件所有内容效率更高; 当文件较大时, 可以一行一行读.
1.2.1 读取文件全部内容
$filename = "/etc/passwd";
open $file, "<", $filename or "cannot open file:$filename\n";
@lines = <$file>;
close $file;
print "$_" foreach @lines;
1.2.2 逐行读取
$filename = "/etc/passwd";
open $file, "<", $filename or "cannot open file:$filename\n";
while(<$file>){
print "$_";
}
close $file
1.3 写文件
- 将程序处理结果写入文件是非常常用的一个操作.
- 写入文件可以使用print, printf输出语句, 只需要在print/printf后面指定文件句柄即可. 默认句柄为STDOUT, 即标准输出.
1.3.1 清空方式写入文件
- 重复执行两次此脚本, 会发现tmp.txt 文件中始终都是一行内容
$filename = "tmp.txt";
open $file, ">", $filename or "cannot open file:$filename\n";
print $file "hello,world\n";
close $file;
1.3.2 追加方式写入文件
- 重复执行脚本多次, 没执行一次, tmp.txt 文件中新增一行hello,world
$filename = "tmp.txt";
open $file, ">>", $filename or "cannot open file:$filename\n";
print $file "hello,world\n";
close $file;
1.3.3 重新向标准输出
- 当文件只需要向一个文件输出内容时,可以直接将标准输出重定向,这样就不用每次在print语句后面添加文件句柄了
$filename = "tmp.txt";
open STDOUT, ">", $filename or "cannot open file:$filename\n";
print "hello,world\n";
2. 文件检测
2.1 常用文件操作符
- perl 提供了很多用于文件判断的操作符, 笔者只列出个人常用的文件操作符:
2.1.1 判断文件权限
测试操作符 |
含义 |
-r |
当前用户对此文件是否拥有可读权限 |
-w |
当前用户对此文件是否拥有可写权限 |
-x |
当前用户对此文件是否拥有可执行权限 |
-o |
此文件所有者是否是当前用户 |
2.1.2 判断文件类型
测试操作符 |
含义 |
-f |
文件是否是普通文件 |
-d |
文件是否是目录文件 |
-l |
文件是否是链接文件 |
2.1.3 判断文件存在
测试操作符 |
含义 |
-e |
文件或目录存在 |
-z |
判断文件内容为空,不能用于判断目录 |
-s |
判断文件或目录存在, 返回文件或目录的大小, 单位为字节 |
2.2 文件操作符组合
- 通常我们可能会对同一个文件的多个属性进行判断, 那么就需要组合文件操作符
2.2.1 逻辑表达式组合
- perl 可以使用and 和 or 表示逻辑与和逻辑或的关系
- 隐式文件句柄 _ 表示上次监测的文件, 用于提升效率
if ( -f $file and -x _ ) {
print "文件$file 存在且可执行\n";
}
2.2.2 栈式组合
if( -f -x $file){
print "文件$file 存在且可执行\n";
}
3. 文件夹操作
- perl语言中对文件夹和文件操作是很简单的, 通常只要拿到文件绝对路径名称即可, 然后使用系统命令对文件进行增删改查即可.
3.1 获取目录下所有文件
- perl 获取目录下所有文件操作是极其简单的,简直不能再简单了
- 通过砖石操作符获取的只是文件名, 返回文件名为局对路径文件名
- 支持shell的通配符, 如*, ?, []等
$dir="/home";
@files=<$dir/*>;
print "$_\n" foreach @files;
3.2 递归文件夹
3.2.1 普通方式
sub recure{
my $file = shift @_;
if( -d $file ){
$cnt_dir++;
my @sub_files = <$file/*>;
foreach my $sub_file (@sub_files ){
&recure($sub_file);
}
}else {
$cnt_file++;
}
}
$dir = "/home/admin/blog";
&recure($dir);
print "files:$cnt_file, dirs:$cnt_dir\n";
3.2.2 极简方式
sub recure{
my $file = shift @_;
if( -d $file ){
$cnt_dir++;
&recure($_) foreach <$file/*>;
}else {
$cnt_file++;
}
}
$dir = "/home/admin/blog";
&recure($dir);
print "files:$cnt_file, dirs:$cnt_dir\n";