Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations TouchToneTommy on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

sorting on hashes

Status
Not open for further replies.

Porshe

Programmer
Jun 5, 2001
38
US
Hi all,

I have this as my data which is comma delimited:

name, address, age, zip, county

If I need to sort my age as my first field to look like this:
age, name, address, zip, county

how could I do it?
thanks,
porshe
 
I'm not sure I understand the question, but, here's a shot.

# elements 0 1 2 3 4
@fields = ('name','address','age','zip','county');
foreach (2,0,1,3,4) { push @new_array, $fields[$_]; }

The new array will have the same contents in different order.

HTH


keep the rudder amid ship and beware the odd typo
 
Here's a couple of questions to help us understand what you need to do better:

Is this a one-record file, or are there multiple records?

Do you really need to rearrange the order of the fields, or do you just need to sort them by age?

Let us know and we'll be happy to help you out. Tracy Dryden
tracy@bydisn.com

Meddle not in the affairs of dragons,
For you are crunchy, and good with mustard.
 
Okay, thanks...
there will be multiple records, and I only need to rearrange the order of the fields depending on the sort condition.
I need to rearrange the order of the fields by putting age first then the rest of the fields. So, I'm thinking of something like this:
>sort age (a)
//sorts by the age field in ascending order.

so it will go from:
name, address, age, zip, county
to:
age, name, address, age, zip, county
//but then it sorts it by ascending order so that ages range from old to young.

Thanks for all your help,
Porshe

 
Sorry I guess I'm being slow today, but I still don't quite understand what you want to do. Do you want to PHYSICALLY change the order of the fields in the record, PHYSICALLY change the order of the records in the file, or just change the order you DISPLAY the fields/records? Tracy Dryden
tracy@bydisn.com

Meddle not in the affairs of dragons,
For you are crunchy, and good with mustard.
 
There aren't to many times when I will go 'out' of Perl to do something with the OS, but, if you are on a UNIX box, the OS sort function will let you specify a delimiter and which field to sort on.

Given this data in a file, data.txt,
bob|35|male
lynn|23|male
lynn|46|female
alex|53|female
john|37|male

this OS command,
sort -t '|' -k 2 data.txt <return>

will produce this output
lynn|23|male
bob|35|male
john|37|male
lynn|46|female
alex|53|female


So,
@records = `sort -t '|' -k 2 dataFile.txt`;

The blue ticks are back ticks. (not hound dogs LOL , I'm to easily amused)

-t defines the delimiter
-k defines which field(s) to sort on



HTH


keep the rudder amid ship and beware the odd typo
 
I just want to change the way I display the results depending on the sorting key.

sorry for the confusion!
 
If you have your data in a file named data.txt and it looks like this,

john,here,38,12345,usa
paco,there,21,54321,honduras
louis,elsewhere,50,france
porshe,somewhere,25,don't know
henry,tahiti,1,??

and, you are using a UNIX OS, this will work.

#!/usr/local/bin/perl
@records = [red]`[/red]sort -t ',' -k 3 data.txt[red]`[/red]; # those are back ticks not quotes
foreach $ordered_rec (@records){ print &quot;$ordered_rec&quot;; }

If you are not using a UNIX OS, let us know and we can add a little to do the sorting with Perl.

HTH

ps - there is a popular breed of hunting dog used widely in the southern US called a 'blue tick hound'. ..... thought readers might have wondered how I was amused with my 'blue ticks' above. ;-)


keep the rudder amid ship and beware the odd typo
 
a non-unix os approach - there must be a more elegant way, but, it is to hard to think up this late in the day..

Code:
#!/usr/local/bin/perl
sub numerically { $a <=> $b; }

open(I,&quot;<data.txt&quot;);
chomp(@recs = <I>);
close I; # I've gone blind!

# reorder the array
foreach (@recs)
    {
    unless (/\w/) { next; }
    my @f = split(/,/,$_);
    my $str = join ',',$f[2],$f[0],$f[1],$f[3],$f[4];
    push @ordered, $str;
    }
@new_order = sort numerically (@ordered);
foreach (@new_order) { print &quot;$_\n&quot;; }

HTH


keep the rudder amid ship and beware the odd typo
 
Here's the way I'd do it:
Code:
open(INPUT, &quot;<input.txt&quot;) || die(&quot;Couldn't open input&quot;);
@data = <INPUT>;
close INPUT;
map(chomp,@data); # remove trailing \n from each rec
@sorted = sort byAge @data;
foreach $rec (@sorted)
   ($name, $addr, $age, $zip, $county) = split(/,/, $rec);
   # print the recs here
}
exit 0;
sub byAge {
   @a = split(/,/,$a);
   @b = split(/,/,$b);
   # age is the 3rd field (subscript = 2)
   return $a[2] <=> $b[2];
}
1;
Tracy Dryden
tracy@bydisn.com

Meddle not in the affairs of dragons,
For you are crunchy, and good with mustard.
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top