willick has asked for the wisdom of the Perl Monks concerning the following question:
I need a way to create array names dynamically from other variables (I would also like to know how to do this with other variables). For instance, I'm running through a loop and need to create a new array for each time I run through the loop. I would think the answer would be simple...but I have yet to find it.
It goes a little something like this:
for ($d = 0; $d <= $#arr_name; $d++) {
#need to create new array with the loop count appended to the name
@arr_new_$d;
#need to push items into new array
push (@arr_new_$d, $something2add);
}
Share your wisdom oh wise ones!!!!!
Edit: chipmunk 2001-10-15
Re: Varying Variable Names
by blakem (Monsignor) on Oct 15, 2001 at 23:36 UTC
|
What you are trying to do is called "symbolic referencing" and is generally considerd to be a bad thing. Instead, you
should probably create a hash that uses your names as keys.
This avoids various scoping issues, and keeps them all in a set so its easier to deal with them as a group. Perhaps
you want something like this:
#!/usr/bin/perl -wT
use strict;
my @arr_name = (10,11,12,13);
my %hash;
for my $d (1..@arr_name) {
my @newarr = ($d..5); # example data
$hash{"new_arr_$d"} = \@newarr; # a new array containing new da
+ta
# with the name "new_arr_$d"
}
for my $key (keys %hash) {
print "$key => ", join(',', @{$hash{$key}}), "\n";
}
=OUTPUT
new_arr_3 => 3,4,5
new_arr_4 => 4,5
new_arr_1 => 1,2,3,4,5
new_arr_2 => 2,3,4,5
-Blake
| [reply] [d/l] |
A reply falls below the community's threshold of quality. You may see it by logging in. |
Re: Varying Variable Names
by wog (Curate) on Oct 15, 2001 at 23:34 UTC
|
You can name variables with other variables, but it is
strongly not reccommend. For why
see this
article.
Instead, you should use an array of arrays,
which is ultimately easier to manage.
(update:) Or, depending upon what you need
to do, you may find you need to, in this case, use a
hash of arrays described in perldsc, along with
many other possible data structures | [reply] |
|
Even if it's strongly not recommended, I need to know how to do it. If I can just name my arrays @array1, @array2, etc it will be easier for what I'm doing.
| [reply] |
|
| [reply] |
|
Convince us that you really need to do it (i.e. tell us a bit more about what you are doing) and we'll help you get it done. I have almost never seen an instance when @array1, @array2, etc. was the right thing to do, nor made things any easier.
-Blake
| [reply] |
Re: Varying Variable Names
by arturo (Vicar) on Oct 15, 2001 at 23:44 UTC
|
It's almost never a good idea to create variable variable names. You have to turn off use strict and you'll very likely confuse yourself.
Use a complex data structure, like a hash of arrays or array of arrays. Well, you can't literally create a hash or array of arrays, but you can do a hash/array of array references, which makes things only a bit more complex. perldoc perlreftut is a good start for learning to use references (see also perldoc perlref and tye's references quick reference), but here's some skeleton code that uses the "array of arrays" method:
# note: you could also do foreach my $d (0 .. $#arr_name)
# on this loop
my @Array_of_arrays;
for (my $d =0; $d < $#arr_name; $d++) {
# following line not necessary, but may help to
# understand
# what's going on: AoA[$d] is a reference to
# an anonymous array
$Array_of_arrays[$d] = [];
# calculate the value $something2add, and
push @{ $Array_of_arrays[$d] }, $something2add;
}
The idea is that, for each of the values $d loops over, $Array_of_arrays[$d] holds a reference to that array. by adding the @{} around that, you de-reference that value (i.e. get the array that it refers to).
Hope this gets you started.
perl -e 'print "How sweet does a rose smell? "; chomp ($n = <STDIN>);
+$rose = "smells sweet to degree $n"; *other_name = *rose; print "$oth
+er_name\n"'
| [reply] [d/l] [select] |
Re: Varying Variable Names
by Zaxo (Archbishop) on Oct 16, 2001 at 04:10 UTC
|
Wouldn't it be nicer to have the number you want to tack on to a name be an actual array index? This gives you an Array-of-Arrays in a compact way:
my @arr_new = map { # generate $something2add from $_
[$something2add];
} @arr_name;
Now, $arr_new[7] is a reference to what your old @arr_new7 would have been.
After Compline, Zaxo | [reply] [d/l] [select] |
Re: Varying Variable Names
by alien_life_form (Pilgrim) on Oct 16, 2001 at 14:30 UTC
|
You can do it without symrefs (but it ain't pretty):
DB<3> $q=1
DB<4> eval "\@arr_$q=('eenie','meenie')"
DB<5> x @arr_1
0 'eenie'
1 'meenie'
If you do this, your program may catch fire, burn, and not run under strict... as others have advised you it might happen. Also, why you'd prefer eval other than symrefs is unclear to me.
OTOH, it looks to me that eval is more explicit - if messier - than symrefs... opinions?
Cheers,
alf
| [reply] |
A reply falls below the community's threshold of quality. You may see it by logging in. |
|
|