On Mon, Oct 29, 2001 at 05:26:39PM +0100, allan wrote:
> > Have you considered using a hash of arrays instead?
> > 
> > push @{$files{'.pl'}}, ':folder_one:byte.pl';
> > push @{$files{'.pl'}}, ':folder_one:byte.pl';
> > push @{$files{'.gif'}}, ':folder_one:some.gif';
> > 
> > etc.
> > 
> > Ronald
> 
> actually yes, though with this syntax:
> 
> $hash_of_file_extensions{".pl"}  = [":folder_one:byte.pl", 1];

That won't work, because you're overwriting the array with each assignment.

> but that didnt help much, because i still could not maintain the insert
> order. it seems the only "nonmodular" way is by a push.
> i have given up with the tie::Hash module as i could not get it to
> maintain the order of the inner hash, the outher hash was no problem.

You would have to tie each inner hash as a Tie::IxHash as well.


> so my current code (which is unfortuantely slow as it is a pretty large
> filesystem) looks something like this (i dont have it right here):
> 
> $hash_of_file_extensions{$extension} = $level; # this is just to grab
> each extension only once, i dont actually use the level variable
> push(@somearray, $extension, $file);
> 
> 
> # then some time consuming stuff like this:
>  
> foreach $key (sort(keys % hash_of_file_extensions)) {
>       print "$hash_of_file_extensions\n";
>       for ($i = 0; $i <= $#somearray; i++) {
>               if ($somearray[$i] eq $key) {
>                   print $somearray[$i+1] \n";
>               }
>       }
> }     

This way you've lost the separation by extension, so you have to search
through the entire list of files for each extension.  Very inefficient.


Here's how I would construct and print the data structure.  I don't know
how you're getting the files, so I've just written in a placeholder
function called get_next_file().  You'll forgive me if I use a shorter
variable name that 'hash_of_file_extensions'.


while (my $file = get_next_file()) {
  my $extension = '';
  $extension = $1 if $file =~ /(\.[^.]+)\z/;

  push @{ $files{$extension} }, $file;
}

foreach my $extension (%files) {
  print "$extension\n";
  foreach my $file (@{ $files{$extension} }) {
    print "  $file\n";
  }
}


The whole data structure, which is a hash of arrays, will look something
like this:

{
  '.pl'  => [ 'foo.pl', 'bar.pl' ],
  '.gif' => [ 'me.gif', 'you.gif' ],
}


Ronald

Reply via email to