Perl(十七)输出和输出(二)文件句柄

一    文件句柄

1)通俗理解-->'文件句柄'用来'对应'要操作的'文件系统中的文件' -->'不太严谨'

   ①  '首先'为要打开的文件'绑定文件句柄'(称为打开文件句柄)  -->'打开'

   ②  '然后'在后续的操作中都通过文件句柄来'操作'对应的文件  -->'操作'

   ③  '最后'关闭文件句柄 -->'关闭'

++++++++++++'更通俗的理解'++++++++++++

可将'文件句柄'看作'Linux中文件描述符'的概念

备注:二者是'不同的',Perl的文件句柄'在层次上对应'于Linux中的标准IO流

  ①  Perl中'特殊的'STDIN、STDOUT、STDERR就是perl中'预定义好的文件句柄',分别表示标准输入、标准输出、标准错误

  ②  Linux上的它们是'默认的'文件描述符'fd=0、fd=1和fd=2'的字符串描述形式,而这几个文件描述符分别'对应文件系统'中的'/dev/stdin'、'/dev/stdout'和'/dev/stderr'设备文件

  ③  小结:Linux上的perl中的'文件句柄'STDIN、STDOUT和STDERR'默认关联的文件'是/dev/stdin、/dev/stdout和'/dev/stderr'

总结:把'文件句柄'想象成通道:perl程序中'IO操作'和'磁盘上文件'的通道,也是Perl进程与外界之间的'I/O联系'的名称

例如:print语句'将数据'通过'某个通道'输出到'对应的文件中'-->'/dev/stdin'

二    文件句柄文件描述符关系

三    Perl中的文件句柄

文件句柄: Perl'进程'与外界之间的'I/O'联系的名称,是"这种关系"的名称,'不是'文件的名称

Perl保留的'六个'特殊文件句柄: STDIN、STOUT、STDEER、DATA、ARGV、ARGVOUT

++++++++++++'标准输入流'++++++++++++

标准输入流: perl程序启动时,'文件句柄STDIN'就是'Perl进程'和它的'输入源'之间的联系

  ①  默认输入来源: 用户的'键盘输入'

  ②  其它输入来源: '文件输入'或是经由'管道读取'到另一个程序的输出

++++++++++++'标准输出流'++++++++++++

  ①  默认输出地:用户的'屏幕'

  ②  其它输出地:送到'文件'或'其它程序'

备注: 标准的流都是源自'Unix标准I/O'库函数

强调: 不要使用'保留的'文件句柄,文件句柄'全大写'

(1)使用Perl默认的裸句柄

'裸句柄'-->类似'<STDIN>'、或者'自定义'裸字

空钻石操作'<>':默认从'命令行'指定的'所有文件读',如果'没有指定','从STDIN读'

(2)使用自定义的裸文件句柄

(3)变量代替文件句柄

++++++++++++++++'标量变量中的文件句柄'++++++++++++++++

特点: Perl'5.6'开始,可以'把文件句柄存放在标量变量中',可以'不使用裸字'

好处: 子程序的参数、放在'数组'、哈希中排序、控制它的'作用域' -->'变量的角度'

      1)裸句柄是'包变量',在'整个文件内'都是有效的

      2)变量方式的文件句柄只在'代码块范围内'有效,出了自己的作用域范围就'失效(自动关闭)'

场景: 应急的'短小脚本'使用'裸字',大型的程序使用变量存储文件句柄

强调: 为了'防止歧义',使用'大括号{}'包围'文件句柄变量'

三    打开文件句柄

1)要'打开文件句柄',使用'open函数'

2)明确'打开文件句柄的目的':为了'读取'、为了'写入'、为了'追加写入' -->这是'操作模式'

3)在open文件时,需要'指明操作模式',此外还要'给定要关联的文件路径',路径可以是'绝对路径'、也可以是相对当前perl程序的'相对路径'

注意:文件句柄'需唯一','不能'出现重名

(1)open函数

1)二参数形式

特点:将'模式符号'和'目标文件'放在一起,二者可以'有空格'

open LOG1,">/tmp/a.log"; 

open LOG1,"> /tmp/a.log"; 

解读:打开一个'文件句柄LOG',这个文件句柄'对应的文件'是/tmp/a.log,'操作模式'是写入

2)三参数形式

++++++++++++语法:open '句柄'  '操作模式'  '文件名'++++++++++++

open LOG1,">","/tmp/a.log";   以'覆盖写入'的方式打开文件/tmp/a.log
open LOG2,">>","/tmp/a.log";  以'追加写入'的方式打开文件/tmp/a.log --> '等价'shell中的'追加重定向'
open LOG3,"<","/tmp/a.log";   打开/tmp/a.log文件,作为'输入源'
open LOG4,"/tmp/a.log";       等价于上面的输入,'默认的模式'就是'输入'

场景:'5.6版本'之后,'推荐'使用该种模式

3)附加参数

功能: 指明'输入'、'输出'的文件编码,则使用':'将"操作模式和编码方式"分割

open LOG1,">:encoding(UTF-8)","/tmp/a.log";   以'UTF-8编码方式写入'数据

open LOG1,"<:encoding(UTF-8)","/tmp/a.log";   以'UTF-8编码方式读入'数据

场景: '中文乱码',最好指定

简写:  open LOG1,"<:utf-8","/tmp/a.log"; --> 不会考虑输入或输出的数据'是否是合法'的UTF-8字符串

+++++++++++'查看perl能理解和处理的字符编码清单'+++++++++++

4)处理有问题的文件句柄

明确: perl自身是'无法打开'外部文件的,它需要'请求操作系统内核',让操作系统来打开文件

因此: 打开文件正确、错误时,'操作系统'都会有相应的'回馈信息'

对于perl来说,'open函数的返回值'就表示正确、错误打开文件

++++++++++++需求:'判断是否正确打开'++++++++++++

场景一:通过'open函数返回值'判断

my $success = open LOG,">","/tmp/a.log";
if(!success){
    exit 1; 'open操作失败'
}
​
场景二:最佳'实践'

open LOG,">","/tmp/a.log"
    or die "open file wrong: $!";

备注: 在'字符串上下文'中,'$!'返回来的是'操作系统'的相应的'出错'消息 --> 使用"$!"可以引用操作系统向perl报告的错误

附加: die 对应的字符串'加上换行符'就'不会'显示'程序名和行号'

++++++++++++++'use autodie'++++++++++++++

备注: '5.10之后'的版本,如果'open失败',会'自动启动die',不用手动指定了

四    关闭文件句柄 

++++++++++++++'文件句柄关闭问题'++++++++++++++

1)一般来说:打开了文件句柄后,在'操作完成后'要及时'关闭文件句柄'以便'节省'操作系统"打开文件数量限制"的资源

关闭句柄'过程':操作系统会将'存在于内存中','尚未写入'的数据'写到磁盘'

2)perl比较'智能':会在某些时候'自动'帮我们'关掉'文件句柄

3)当'打开'一个文件句柄后,'再'去'打开这个文件句柄'时,perl'会先关闭'这个文件句柄'再打开这个'文件句柄,这称为"文件句柄的reopen"-->类似'nginx的reopen'

特点:它只是'隐式地'关闭并重新打开,perl并'不认为'中间涉及了关闭操作 -->例如'reopen时行号'不会重置

备注:关闭文件句柄'错误'也可以通过'die'捕捉

close  LOG;

五   使用文件句柄

(1)读取文件数据

(2)写入数据到文件

备注: 在使用'print、say、printf'的时候,在这'几个关键字后'面接上'文件句柄'即表示本输出语句'写入到'此文件句柄中

'select'关键字自己选一个默认的'输出文件句柄' --> '了解即可'

六  报错处理

在程序中'处理中文等宽字符'时,perl'不能识别'要处理的内容

①  方式一

use utf8;
binmode(STDIN, ':encoding(utf8)');
binmode(STDOUT, ':encoding(utf8)');
binmode(STDERR, ':encoding(utf8)');

②  方式二

use utf8;
#  标准输入、输出、错误皆用utf-8编码格式进行编码 -->这里是'标准输入'
use open ":encoding(utf-8)",":std";

参考博客

高级文件句柄模式

 
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值