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 Mike Lewis on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

Converting from Row to column

Status
Not open for further replies.

sdslrn123

Technical User
Jan 17, 2006
78
GB
A = 1
A = 2
A = 3

B = 5
B = 1
B = 7

e.t.c
C = .....


Is there a way to convert this format to:
A = 1,2,3
B = 5,1,7
C = ...
.
.
.
Z = ...



I am thinking
while in data file
split each line to letters and numbers.
if next letter matches previous letter push into an array

otherwise create a new array called B?
 
Create a hash of arrays. The keys of the hash are the letters and the values are arrays of the numbers associated with each letter. Google for perllol for more on multidimensional data structures in Perl.
 
Using Hashes:
Code:
my %lines=();
open DATAFILE, "input.txt";
while(<DATAFILE>) {
  chomp;
  my ($letter,$number) = split(/=/);
  $letter =~ s/\s+$//;
  $number =~ s/^\s+//;
  if(defined($lines{$letter})) {
    $lines{$letter} .= ",$number";
  } else {
    $lines{$letter} = "$letter=$number";
  }
}
close DATAFILE;

foreach (keys %lines) {
  print "$lines{$_}\n";
}
 
Code:
  my ($letter,$number) = split(/=/);
  $letter =~ s/\s+$//;
  $number =~ s/^\s+//;
Why force yourself to remove the spaces later when you can just include them in your split?
Code:
my ( $letter, $number ) = split( / = / );
 
Here is the hash of arrays solution.

Code:
my %values;
while (<DATA>) {
    chomp;
    my ($key,$val) = split/ = /;
    push @{$values{$key}},$val;
}
foreach my $key (keys %values) {
    next if !$key;
    print "$key = " . join(',', @{$values{$key}}) . "\n";

}

__DATA__
A = 1
A = 2
A = 3

B = 5
B = 1
B = 7
 
Ishnid said:
Why force yourself to remove the spaces later when you can just include them in your split?

Because they may or may not be there.
 
There's nothing in the OP's post to suggest that they won't be there. They're in the data format that's posted.

If you are allowing for them to be absent, then you can include that in the split too:
Code:
my ( $letter, $number ) = split( / ?= ?/ );
 
Or you can skip the split and just use a regex:
Code:
while (<DATA>) {
    push(@{$values{$1}}, $2) if /(\w+)\s*=\s*(\w+)/;
}
One thing that I don't think was addressed is the order of the keys. Sorting them is easy as far as the sample data is concerned, but if the order of the keys in the real data isn't easily reproduced, something (an array probably) will need to be implemented to track the order the keys are read.
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top