http://qs321.pair.com?node_id=178610


in reply to Improper use of global variable? (was: Global variables)

Well, lets say you dont want to use a global variable, suppose your binary tree is composed of hash elements with "left" and "right" keys (where left<=mid<right) you might try something like this:
sub find_key_dupes { my $binary_tree=shift; my $key=shift; my $sub; my @dupes; $sub=sub { my $node=shift; return unless $node; if ($node->{key} lt $key) { $sub->($node->{right}); } else { push @dupes,$node if $node->{key} eq $key; $sub->($node->{left}); } }; $sub->($binary_tree); return \@dupes; }
This is using closures to simulate the effect of a Pascal's nested subroutines. Its a nice trick for having lexically scoped vars acting as globals to a recursive subroutine. This avoids having to pass them as parameters. Also, my guess is that you could avoid recursion entirely and do this with one sub (without nesting) using iterative techniques, which would be faster but probably slightly more complicated code.

Oh and I whipped that code out pretty fast, so its untested but you get the idea I hope. (And I hope its correct ;-)

Yves / DeMerphq
---
Writing a good benchmark isnt as easy as it might look.

Replies are listed 'Best First'.
Re: Re: Global variables *plug*
by broquaint (Abbot) on Jul 01, 2002 at 17:37 UTC
    And here's a perfect situation to take advantage of Sub::Lexical's ability to emulate nested subs ...
    use Sub::Lexical; sub find_key_dupes { my $binary_tree=shift; my $key=shift; my @dupes; my sub get_dupes($) { my $node=shift; return unless $node; if ($node->{key} lt $key) { get_dupes($node->{right}); } else { push @dupes,$node if $node->{key} eq $key; get_dupes($node->{left}); } } get_dupes($binary_tree); return \@dupes; }
    Thanks demerphq, I'll be using this as valid example code in future. <simpsons voice="Mr. Burns">ehhhxcellent</simpsons>.
    HTH

    _________
    broquaint