在perl中打开文件进行读写(不附加)

时间:2010-12-19 04:48:58

标签: perl file file-io

标准的perl库是否有任何方法可以打开文件并对其进行编辑,而无需关闭它然后再打开它?我所知道的只是将文件读入一个字符串中关闭文件,然后用一个新文件覆盖该文件;或者读取然后附加到文件的末尾。

以下目前有效;我必须打开它并关闭它两次,而不是一次:

#!/usr/bin/perl
use warnings; use strict;
use utf8; binmode(STDIN, ":utf8"); binmode(STDOUT, ":utf8");
use IO::File; use Cwd; my $owd = getcwd()."/"; # OriginalWorkingDirectory
use Text::Tabs qw(expand unexpand);
$Text::Tabs::tabstop = 4; #sets the number of spaces in a tab

opendir (DIR, $owd) || die "$!";
my @files = grep {/(.*)\.(c|cpp|h|java)/}  readdir DIR;
foreach my $x (@files){
    my $str;
    my $fh = new IO::File("+<".$owd.$x);
    if (defined $fh){
        while (<$fh>){ $str .= $_; }
        $str =~ s/( |\t)+\n/\n/mgos;#removes trailing spaces or tabs
        $str = expand($str);#convert tabs to spaces
        $str =~ s/\/\/(.*?)\n/\/\*$1\*\/\n/mgos;#make all comments multi-line.
        #print $fh $str;#this just appends to the file
        close $fh;
    }
    $fh = new IO::File(" >".$owd.$x);
    if (defined $fh){
        print $fh $str; #this just appends to the file
        undef $str; undef $fh; # automatically closes the file
    }
}

1 个答案:

答案 0 :(得分:15)

您已经使用模式<+打开文件进行读写,您只是没有对它做任何有用的事情 - 如果您想要替换文件的内容而不是写入当前位置(文件末尾)然后您应该seek回到开头,写下您需要的内容,然后truncate以确保如果您缩短文件时没有遗留任何内容

但是,由于你要做的是对文件进行过滤,我是否可以建议您使用perl的inplace编辑扩展,而不是自己完成所有工作?

#!perl
use strict;
use warnings;
use Text::Tabs qw(expand unexpand);
$Text::Tabs::tabstop = 4;

my @files = glob("*.c *.h *.cpp *.java");

{
   local $^I = ""; # Enable in-place editing.
   local @ARGV = @files; # Set files to operate on.
   while (<>) {
      s/( |\t)+$//g; # Remove trailing tabs and spaces
      $_ = expand($_); # Expand tabs
      s{//(.*)$}{/*$1*/}g; # Turn //comments into /*comments*/
      print;
    }
}

这就是你需要的所有代码 - perl处理其余的代码。设置$^I variable等同于使用-i commandline flag。我对代码进行了一些更改 - use utf8对源代码中没有文字UTF-8的程序没有任何作用,binmode stdin和stdout对从不使用stdin的程序没有任何作用或者stdout,保存CWD对于从不chdir s的程序没有任何作用。没有理由一次性读取所有文件所以我将其更改为linewise,并使正则表达式不那么笨拙(顺便说一句,/o正则表达式修饰符现在几乎没有任何好处,除了添加硬 - 找到代码中的错误。)