如何使用Perl在同一文本文件上进行读写

时间:2015-10-15 14:35:11

标签: perl file hash

我在Read Write模式下打开一个文件(+<)并遍历保存上一行的每一行。基于前一行我试图修改当前行似乎不起作用。

我的输入:我有一个学生哈希,其中包含姓名,地址和DOB。我有一个文件,其中学生信息放在开始(本地或国际)和结束标签之间。

请在下面找到我输入的txt文件:

+++++++++++++++++++++++++++ViSHWASCHOOL++++++++++++++++++++++++++
student database system.... xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++  
xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx 
some text here.... filled with xxx
for school data security ++++++
XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX


/begin Local
         Karen
         ""
         mothername Mawna
         fathername Gildixon
         total_marks 400 
         percent 90%  /end Local

/begin Local
         John
         ""
         fathername Alister
         mothername Linda
         total_marks 320 
         percent 72%  /end Local        

/begin Local
         Katie
         "24 lenin street florida us"
         mothername Sandra
         fathername Manwel
         total_marks 450 
         percent 95%        /end Local

/begin International
         Boris
         ""
         mothername laumra
         fathername deaol
         total_marks 490 
         percent 98%  /end International

/begin International
         hawo binco
         "honko , china"
         mothername ""
         fathername ""
         total_marks 500 
         percent 100%  /end International

任务:现在我要做的是填写学生档案中的所有地址,在学生姓名后面找到空的“”。保留学生档案的所有空格和格式。 。

我的Perl代码:

use strict;
use warnings;
use Data::Dumper;

my %student_hash;
my $student_report = "StudentReport.csv";

         %student_hash = (
                'RollNummber1' => {
                                   'studentname' => 'Boris',
                                   'address' => ['Vietnam',
                                                 'local'
                                                ],
                                   'DOB' => '5june2000'

                                   },
                'RollNummber2' => {
                                   'studentname' => 'John',
                                   'address' => [ 
                                                 '4th/floor',
                                                 'Culverdown/Street',
                                                 'WestHam',
                                                 'UK.',
                                                ],
                                   'DOB' => '2feb2000'

                                   },
                'RollNummber3' => {
                                   'studentname' => 'Karen',
                                   'DOB' => '5march2000'

                                  }
               );



my $studentfile = "testfile.txt";
my @studenttype = ('International', 'Local');

foreach my $type (@studenttype) {
      process_studentfile( $type, $studentfile );
   }
print "\nStudent Files are now filled with addresses\n";

sub process_studentfile {

my $type = shift;
my $studentfile = shift;
open(my $file,'+<',$studentfile);

my $previous_line = "";
while(my $current_line = <$file>){
   if($current_line =~ /""/) {
   foreach my $key(%student_hash) {
       foreach my $name(keys %{$student_hash{$key}}) {
            if($previous_line =~ /$student_hash{$key}{'studentname'}/) {
                print $file join(",",@{$student_hash{$key}->{address}});
            }
       }
    }
    $previous_line = $_; 
    }
   }
   close $file;
}

**注意:**我以不同的方式对此感到厌倦,但仍然无法完成任务。可以在不使用任何cpan模块的情况下帮助一些标准模块吗?

1 个答案:

答案 0 :(得分:1)

在尝试重写的同时使用while ( <$fh> )存在根本问题。因为while正在根据分隔符$/读取文件块。但文件在字节中工作。

来自perldoc open

  

您通常不能使用读写模式来更新文本文件,因为它们具有可变长度的记录。请参阅perlrun中的-i开关以获得更好的方法。

因此,如果你写一个不同的长度线,一切都有点麻烦。它对文本文件效果不佳,因为你有可变长度的“记录”。

您可以使用seek浏览文件,但请记住,您实际上是在每个字节(字符)的基础上进行覆盖。

或者只是使用临时文件,并在完成后将其复制到源代码上。这就是-i的作用。 (这也意味着您损坏数据的风险要低得多,因为如果出现问题,您可以优雅地拯救)