I am new to Scripting language.
I want to split a file and create several subfiles using Perl script.
Example :
File format :
Sourcename ID Date Nbr
SU IMYFDJ 9/17/2012 5552159976555
SU BWZMIG 9/14/2012 1952257857887
AR PEHQDF 11/26/2012 0442045903874
AR ELIOAA 12/31/2012 0442121341024
I want to split this files by Sourcename.
As this has two source name, so it will be splitting into two.
File 1 (after splitting) :
Sourcename ID Date Nbr
SU IMYFDJ 9/17/2012 5552159976555
SU BWZMIG 9/14/2012 1952257857887
File 2 (after splitting) :
Sourcename ID Date Nbr
AR PEHQDF 11/26/2012 0442045903874
AR ELIOAA 12/31/2012 0442121341024
A Perl program doing the job
file025 (tabs have been replaces by spaces):
Sourcename ID Date Nbr
SU IMYFDJ 9/17/2012 5552159976555
SU BWZMIG 9/14/2012 1952257857887
AR PEHQDF 11/26/2012 0442045903874
AR ELIOAA 12/31/2012 0442121341024
Program :
#!/usr/bin/perl -w
use strict;
my $cur_dir = $ENV{PWD};
my $filename = "$cur_dir/$ARGV[0]";
my ($record,$header,$i,@fields,%files);
open(FILEIN,"<$filename") or die"open: $!";
while( defined( $record = <FILEIN> ) ) {
chomp $record;
$header=$record if (!defined $header);
$i++;
if($i > 1) {
@fields=split(/ /,$record);
# if file do not exits, create it and write header
if(! exists( $files{$fields[0]}) ) {
$files{$fields[0]} = "$fields[0].file";
open (FILEOUT, "> /tmp/$files{$fields[0]}") ||
die "FATAL: cannot open \"$files{$fields[0]}\" for writing: $!\n";
print FILEOUT "$header\n";
close(FILEOUT);
}
# append record to file
open (FILEOUT, ">> /tmp/$files{$fields[0]}") ||
die "FATAL: cannot open \"$files{$fields[0]}\" for writing: $!\n";
print FILEOUT "$record\n";
close(FILEOUT);
}
}
close(FILEIN);
Outputs :
/tmp %cat SU.file
Sourcename ID Date Nbr
SU IMYFDJ 9/17/2012 5552159976555
SU BWZMIG 9/14/2012 1952257857887
/tmp %cat AR.file
Sourcename ID Date Nbr
AR PEHQDF 11/26/2012 0442045903874
AR ELIOAA 12/31/2012 0442121341024
In the file if I am using delimiter '|' instead of space,
It is giving output file name as single letter.
Example :
$i++;
if($i > 1) {
@fields=split(/|/,$record);
# if file do not exits, create it and write header
if(! exists( $files{$fields[0]}) ) {
$files{$fields[0]} = "$fields[0].file";
open (FILEOUT, "> /tmp/$files{$fields[0]}") ||
die "FATAL: cannot open \"$files{$fields[0]}\" for writing: $!\n";
print FILEOUT "$header\n";
close(FILEOUT);
Result :
Filename :
S.file
Sometimes I have Sourcename more than 2 letters also.
Sourcename ID Date Nbr
SU|IMYFDJ|9/17/2012|5552159976555
SU|BWZMIG|9/14/2012|1952257857887
AR|PEHQDF|11/26/2012|0442045903874
AR|ELIOAA|12/31/2012|0442121341024
you must escape the pipe "|" in the splitting line that way :
Hi there, hereafter the code with the zip output, working good on an Aix system.
Each file name created is stored in an array (@fileLst) and at the end of the program, all files of the array are zipped into an unique archive :
:
#!/usr/bin/perl -w
use strict;
my $cur_dir = $ENV{PWD};
my $filename = "$cur_dir/$ARGV[0]";
my ($record,$header,$i,@fields,%files,$key,@fileLst);
open(FILEIN,"<$filename") or die"open: $!";
while( defined( $record = <FILEIN> ) ) {
chomp $record;
$header=$record if (!defined $header);
$i++;
if($i > 1) {
@fields=split(/\|/,$record);
if(! exists( $files{$fields[0]}) ) {
$files{$fields[0]} = "$fields[0].file";
open (FILEOUT, "> /tmp/$files{$fields[0]}") ||
die "FATAL: cannot open \"$files{$fields[0]}\" for writing: $!\n";
push(@fileLst,"/tmp/$files{$fields[0]}");
print FILEOUT "$header\n";
close(FILEOUT);
}
open (FILEOUT, ">> /tmp/$files{$fields[0]}") ||
die "FATAL: cannot open \"$files{$fields[0]}\" for writing: $!\n";
print FILEOUT "$record\n";
close(FILEOUT);
}
}
close(FILEIN);
foreach (@fileLst) {
system("zip /tmp/zipfile.zip $_");
}