On May 26, 8:17 am, [EMAIL PROTECTED] (Pauld) wrote:
> ive read a load of data in  from a CSV file with Text::CSV and ended
> up with a hash (%hash) where the keys are the column labels.
> my  @headings=split(/,/,$rows[0])

You're use()'ing Text::CSV, but you're not actually using Text::CSV.
Why?

> and then
>
> for (my $j=1;$j<$#rows;$j++)

Is there a reason you're ignoring the last row completely?

> {
> my $status  = $csv->parse ($rows[$j]);   # parse a CSV string into
> fields

Storing the status is rather pointless if you don't bother actually
checking it. . .

> my @columns = $csv->fields ();           # get the parsed fields
>
> for (my $i=0;$i<$#columns;$i++)

Now you're ignoring the last column.  Do you understand that $#foo is
the *last index* of @foo, and so looping until less than $#foo stops
before the last element?

>   {$hash{$headings[$i]}=$columns[$i];}

Of course, that entire loop would be better served to be a hash
slice...

>
> I want to  process the data once its grouped by the date field present
> in $hash. So i think I want a hash of dates  where the key is that
> date field
> I  push onto the value the hashes of the records that contain the date
>
> push @{$Hofdates{$hash{DATE}}},\%hash;
>
> but im having a problem working out how to access the  individual
> items in the  hashes that are elements of the array

You should read:
perldoc perllol
perldoc perldsc

Go step by step:
(1) %Hofdates is your overall hash.
(2) $Hofdates{'2007-05-26'} is one element of the hash.  That element
is a reference to an array.
(3) @{$Hofdates{'2007-05-26'}} is the array that (2) references.
(4) ${$Hofdates{'2007-05-26'}}[0] is the first element of (3).  That
element is a reference to a hash.
(5) %{${$Hofdates{'2007-05-26'}}[0]} is the hash that (4) references.
(6) ${${$Hofdates{'2007-05-26'}}[0]}{NAME} is the value of (5) at the
key 'NAME'
(7) $Hofdates{'2007-05-26'}[0]{NAME} is the same as (6), but with all
unnecessary punctuation removed.  (See perldocs listed above)

Once you get used to Perl's multi-level structures, you'll find you
don't need to go through this process, as the end result just "makes
sense".

Please note, whenever possible, please try to post a short-but-
complete script that demonstrates what you're trying to do.  That way
we can help you see what you might have done wrong.  For example:

#!/usr/bin/perl
use strict;
use warnings;
use Text::CSV;
use Data::Dumper;

my $csv = Text::CSV->new();
my %records_for;

my $heading = <DATA>;
$csv->parse($heading)
  or die "Could not parse '$heading'.  Failed on " . $csv-
>error_input;
my @heading = $csv->fields();
while (my $line = <DATA>) {
  $csv->parse($line)
    or die "Could not parse line $..  Failed on " . $csv->error_input;
  my @columns = $csv->fields();
  my %hash;
  #use a hash slice rather than a for loop.
  @[EMAIL PROTECTED] = @columns;
  push @{$records_for{$hash{DATE}}}, \%hash;
}

#Take a look at your structure.
print Dumper(\%records_for);

#Get the name of the 2nd record with date '2007-05-26';
print $records_for{'2007-05-26'}[1]{'NAME'}, "\n";

#or, get the names of all records:
foreach my $date (keys %records_for) {
  my $i = 0;
  foreach my $record (@{$records_for{$date}}) {
    print "$date($i): $record->{NAME}\n";
    $i++;
  }
}


__DATA__
NAME,DATE,COLOR,SIZE
Paul,2007-05-26,blue,large
John,2007-04-21,red,small
Mary,2007-05-26,orange,medium
Peter,2006-01-30,blue,small


Hope this helps,
Paul Lalli


-- 
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]
http://learn.perl.org/


Reply via email to