The '\' operator is Perl's way of saying "please give me a reference to the thing following". So
is an expression whose value is a reference pointing to the array @foo.\@foo
References are scalars, so an expression like this
passes three different arrays to my_sub. If you left off the "\", you'd get one big array of all the elements, which is not what the algorithm wants. Notice how @_ is broken up into 3 scalars? Those are the three references to the arrays coming in.my_sub(\@alpha, \@beta, \@gamma);
Second, the funny-looking sigils are actually dereferences of the references we passed in. Remember, what we got was references, which point at something; they can't be used themselves. You dereference a scalar by putting the appropriate sigil in front of it. So if we have the following:
we could dereference each of these by putting the appropriate sigil in front:my $hashref = \%myhash; my $arrayref = \@myarray; my $scalarref = \$myscalar;
The usage $#$foo says "Please treat whatever is in $foo as an array reference, and do a $# on that array." (This particular usage is really weird; I've actually never seen it used before!) You've seen $$ (please give me the scalar this reference points to) and @$ (please give me the array this reference points to).my %newhash = %$hashref; my @newarray = @$hashref; my $newscalar = $$scalarref;
It's important to remember that a reference to an array, when dereferenced, actually means "remember @bar back in the main program? Well, I want you to do these operations on that particular array." So @$chunks really means "I want @chunks back in the main program". (The names don't have to be the same; the programmer who wrote this just decided to write it that way. More confusing, in my book.)
Last, remember that when you call a subroutine, you have to return from it, so each of those calls will (eventually) return: the bottoming-out test is
When this happens, the code does thisif ($idx2 >= $idx1)
and then returns by falling out of the bottom of the subroutine.$size = $#$fbits - $idx2; push @$chunks, [ (bits2num( [ @prefix, (split //, '0' x $size) ])), @$ +fbits - $size ];
Since we have a bottoming-out criterion, then the two calls to do_chunk mean "please carry out the do_chunk on this set of data, and when that's eventually done, run it a second time on this other data, then fall out the bottom to return (again)".
A couple of other notes:
This is not the world's best clearest code. Because the code insists on doing all the work in the original arrays, it's a lot more complicated and uses a lot more reference expressions. If it were me, I'd try to find a way to do it by capturing the arrays in local copies, manipulating those, and then returning values (probably references to arrays inside the code we just returned from - yes, you can do that; if you call a sub, take a reference to a my variable inside it, and then return that reference, Perl figures that variable was important to you and keeps it around until either the variable holding the reference in the caller gets set to some other value, or the variable holding the reference goes out of scope).
You might find it interesting to run this code from a little test program under the debugger, breaking at the beginning of do_chunk, then doing x @_ to see how the arrays change on each call.
In reply to Re: Total Syntax Confusion Plus
by pemungkah
in thread Total Syntax Confusion Plus
by RobertJ
| For: | Use: | ||
| & | & | ||
| < | < | ||
| > | > | ||
| [ | [ | ||
| ] | ] |