?
Solved

Sorting & displaying a file.

Posted on 2000-03-24
6
Medium Priority
?
237 Views
Last Modified: 2011-09-20
The following code snppet opens a flat file with a list of 4 pipe delimited fields terminated with a new line and displays them in sequential order.

QUESTION:

How would I display the file contents say, SORTED on field 1 ($f1) and NOT sequentially ????

I would like a working code example.
Thanks, In advance.

#!/usr/bin/perl

$dbase = "/home/blah/dbase.txt";

print "Content-type: text/html\n\n";
print "<html><head><title></title></head>\n";
print "<body bgcolor=#FFFFFF\n";
print "<br>\n";

open(FILE,"$dbase") || die "Cannot Open Database File: $!\n";

&dall;

print "<br></body></html>\n";
close(FILE);
exit;

# Display all records
sub dall {
 while(<FILE>) {
 chop;
 @all = split(/\n/);
  foreach $line(@all) {
   local($f1,$f2,$f3,$f4)=split (/|/,$line);
   &display;
  }
 }
}

# Display results
sub display {
print "$f1, $f2, $f3, $f4\n";
print "<br>\n";
}

0
Comment
Question by:haast
[X]
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
  • 5
6 Comments
 
LVL 16

Accepted Solution

by:
maneshr earned 800 total points
ID: 2656112
here is your modified script

the sort sub routine i have provided is very flexible. using this you can sort on any column numerically or alphabetically, in ascending or descending order.

=====================================
#!/usr/bin/perl

$dbase = "/home/blah/dbase.txt";

print "Content-type: text/html\n\n";
print "<html><head><title></title></head>\n";
print "<body bgcolor=#FFFFFF\n";
print "<br>\n";

open(FILE,"$dbase") || die "Cannot Open Database File: $!\n";
@all=<FILE>; ## Read the entire file into an array. every line of the file is
## an element in the array.
close(FILE);

##  Column num (starting from 1), type of sort
##  n = numeric, a = alphabetic ...
##  ... Sort order "a" = ascending, "d"= descending & ...
##  ... Array to sort
@all=&my_sort(1,"n","d",@all);

foreach $line(@all) {
  local($f1,$f2,$f3,$f4)=split (/|/,$line);
  print "$f1, $f2, $f3, $f4\n";
  print "<br>\n";
}

print "<br></body></html>\n";

##  Subroutine that does the actual sort.
##  Accepts 4 params viz. the column number to sort
##  Column no starts with 1. The type of sort numeric or alphabetic
##  Finally the sort order is required. Default order is ascending
##  The array that needs to be sorted.
sub my_sort{
  ($col,$type,$sort_order,@arr)=@_;

  ##  Deduct 1 from the column.
  ##  We do this because in PERL array subscript starts with 0.
  ##  So in human terms when we say column 2 it means column 1 in PERL terms!!
  $col--;

  ##  To take care of conditions where user has passed anything other
  ##  ... than a "n" or "N". Eg. if the user has said &my_sort(3,"z",@array,"a"
), we ignore the z and perform an alphabetic sort ("a").
  $type="a" if $type!~ /^n$/i;  ##  Default Alphabetic sort

  ##  To take care of conditions where user has passed anything other
  ##  ... than a "d" or "D". Eg. if the user has said &my_sort(3,"z",@array,"q"
), we ignore the q and sort in ascending order("a").
  $sort_order="a" if $sort_order!~ /^d$/i;  ##  Default Ascending Sort order

  ##  Process every element of the array
  foreach(@arr){
    ##  Split every line using | as the delimiter.
    @tmp=split(/\|/,$_);
    ##  After we split we know how many columns are ..
    ##  ... present in every record. Now we have to ...
    ##  ... take care of situations where the user might want ..
    ##  ... to sort on non-existant or invalid columns.
    ##  Eg. Each record has 6 columns and the user has passed 7 or 8
    ##  ... or -1 etc...

    return 0 if ($col<0 || $col>(scalar @tmp)); ## Invalid col no.

    ##  This is important. We take the column that the user wants ...
    ##  ... to sort on and pre-pend it to the record itself.

    ##  Let's say the record is ...
    # Toronto|Jeff|jeff@hyrum.net|98|571803
    ##  ...& the user wants to sort on the 2nd column (PERL subscript 1).
    $new_arr=join('|',$tmp[$col],$_);
    ##  After the above the record will be...
    # Jeff|Toronto|Jeff|jeff@hyrum.net|98|571803

    ##  Store this new record in an array
    push(@new_arr,$new_arr);
  }

  ##  Determine the type of sort
 if ($type=~ /^n$/i){    ##  Numeric Sort
    if ($sort_order=~ /^d$/i){  ##  Descending sort requested
      ##  Sort the array by number using the bynum subroutine
      @new_arr=reverse sort bynum @new_arr
    }else{  ##  Default, Ascending sort order requested
      @new_arr=sort bynum @new_arr
    }
  }else{  ##  Alphabetic sort
    if ($sort_order=~ /^d$/i){  ##  Descending sort requested
      ##  Sort the array by alphabets using the byalp subroutine
      @new_arr=reverse sort byalp @new_arr
    }else{  ##  Default, Ascending sort order requested
      @new_arr=sort byalp @new_arr
    }
  }

  @arr="";  ##  Re initialize the array
  ##  Remember our sort is done, but we still have that...
  ##  ...extra column at the beggining that we must remove!!
  foreach(@new_arr){
    ##  Split every line using | as the delimiter.
    @tmp=split(/\|/,$_);
    shift(@tmp);  ##  Remove that 1st column
    ##  So before the shift if we had....
    # Jeff|Toronto|Jeff|jeff@hyrum.net|98|571803
    ##  After th shift we will have...
    # Toronto|Jeff|jeff@hyrum.net|98|571803

    ##  Join the array as one record...
    $new_arr=join('|',@tmp);
    ##  ...& store it in another array.
    push(@arr,$new_arr);
  }

  ##  Return the final array (in sorted order)
  return @arr;
}

sub bynum{ $a <=> $b;}

sub byalp{ $a cmp $b;}
0
 

Author Comment

by:haast
ID: 2656220
Hang on, I will try it.....
0
 

Author Comment

by:haast
ID: 2656253
Maneshr, that is excellent, I want to award you the points for this.

I am a newbie and I really appreciate your help, I would like to ask you ONE more question, and either add 100 more points to this or ask a NEW one (please advise !!!!).

It is a variation on my original one.

#!/usr/bin/perl

$dbase = "/home/blah/dbase.txt";

# Parse Form
read(STDIN, $input, $ENV{'CONTENT_LENGTH'});
@pairs = split(/&/, $input);
foreach $pair (@pairs) {
($name, $value) = split(/=/, $pair);
$name =~ tr/+/ /;
$name =~ s/%([a-fA-F0-9][a-fA-F0-9])/pack("C", hex($1))/eg;
$value =~ tr/+/ /;
$value =~ s/%([a-fA-F0-9][a-fA-F0-9])/pack("C", hex($1))/eg;
$FORM{$name} = $value;
}

# Translate Hash References
$find  = $FORM{'term'};

print "Content-type: text/html\n\n";
print "<html><head><title></title></head>\n";
print "<body bgcolor=#FFFFFF\n";
print "<br>\n";

open(FILE,"$dbase") || die "Cannot Open Database File: $!\n";

&search;

print "<br></body></html>\n";
close(FILE);
exit;

# Search all records for matches
sub search {
$match = 0;
 while(<FILE>) {
 chop;
 @all = split(/\n/);
  foreach $line(@all) {
   local($f1,$f2,$f3,$f4)=split (/|/,$line);

    if($find eq $f1){
      &display;
    }
  }
 }
}

# Display matched results
sub display {
print "$f1, $f2, $f3, $f4\n";
print "<br>\n";
}

-------------------
MY NEW QUESTION IS:

How would I sort the results of the matched records ($find eq $f1) , and display them say, in ascending alfa sorted order based on field $f2.

Thanks !!!!






0
Technology Partners: We Want Your Opinion!

We value your feedback.

Take our survey and automatically be enter to win anyone of the following:
Yeti Cooler, Amazon eGift Card, and Movie eGift Card!

 

Author Comment

by:haast
ID: 2656256
Adjusted points from 100 to 200
0
 

Author Comment

by:haast
ID: 2657268
Maneshr, even if you do not answer the second part of my question, please collect your points. Your help is much appreciated.
0
 

Author Comment

by:haast
ID: 2657634
Maneshr, I have figured my second question out, PLEASE collect your points.

Thanks !!
0

Featured Post

On Demand Webinar - Networking for the Cloud Era

This webinar discusses:
-Common barriers companies experience when moving to the cloud
-How SD-WAN changes the way we look at networks
-Best practices customers should employ moving forward with cloud migration
-What happens behind the scenes of SteelConnect’s one-click button

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

I have been pestered over the years to produce and distribute regular data extracts, and often the request have explicitly requested the data be emailed as an Excel attachement; specifically Excel, as it appears: CSV files confuse (no Red or Green h…
In the distant past (last year) I hacked together a little toy that would allow a couple of Manager types to query, preview, and extract data from a number of MongoDB instances, to their tool of choice: Excel (http://dilbert.com/strips/comic/2007-08…
Explain concepts important to validation of email addresses with regular expressions. Applies to most languages/tools that uses regular expressions. Consider email address RFCs: Look at HTML5 form input element (with type=email) regex pattern: T…
Six Sigma Control Plans

800 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question