in reply to Package-Level Variables

This is meant for rough "Rosetta" comparison, and clearly the two languages have some very different idioms and distinct semantics on various features.

Foo.pm:
package Foo; our @ISA = qw(Exporter Phoo); our $Bar = 6; my $Whig = 5; sub new { my $count if 0; $count++; my $self = { }; $self->{baz} = 4; return bless($self, shift()); } sub foo { my $self = shift; my $arg = shift; local $Whig = 3; $self->my_Phoo_func($Whig, $arg, $/); }
Foo.cpp:
#include "Foo.h" // class Foo : public Phoo { ... }; static int Foo::Bar = 6; static int Whig = 5; Foo::Foo() { static int count = 0; count++; this->baz = 4; } void Foo::foo(int arg) { int save_Whig = Whig; Whig = 3; this->my_Phoo_func(Whig, arg, "\n"); Whig = save_Whig; }

I mention the C++ this twice for clarity, though these are implicit, not required, and rarely mentioned in C++. Note that static means something entirely different inside a C++ function versus outside a function. The Perl hack my $foo if 0; is not something I recommend, but does emulate C++'s static lexical variables (or as Larry calls them, "persistent" between calls).

--
[ e d @ h a l l e y . c c ]

Replies are listed 'Best First'.
Re: Re: Package-Level Variables
by sauoq (Abbot) on Jul 25, 2003 at 20:42 UTC
    my $count if 0;

    Ugh... do you actually use that? I thought that was only an unintended side-effect of how scratchpads are implemented. Am I confused on that point?

    I would use a named closure for emulating static vars

    { my $static; sub count { $static++ } }

    Also, I think "use Foo;" is more analogous to "#include <Foo.h>" than "package Foo;" is.

    -sauoq
    "My two cents aren't worth a dime.";
    
      One, as mentioned, I don't recommend the hack for persistent variables. I think it's interesting. I haven't seen your method in use, but I've seen the hack.

      Two, you wouldn't use Foo; inside Foo.pm. This Rosetta line is the statement which establishes the namespace for the subsequent implementation code. (Hence the comment following which shows what the header file implies.) In C++, both the user and the implementor of a class typically include the header file; in Perl, only the user would 'use' the file as if declaring the intent to call upon its interface.

      --
      [ e d @ h a l l e y . c c ]

        Two, you wouldn't use Foo; inside Foo.pm.

        True, but you that's because we don't separate the interface from the implementation in Perl. Even in C++, you could put the whole implementation in the header file if you chose to.

        This Rosetta line is the statement which establishes the namespace for the subsequent implementation code.

        But that's not at all what it does in C++ and, in fact, it wouldn't be uncommon to see various other #include's in the source file containing the implementation.

        I stand by my original assertion. #include <Foo.h>; is much more analagous to use Foo; in Perl. In both cases, you are stating your intent to use the interface provided by the class/module/library/whatever called "Foo".

        -sauoq
        "My two cents aren't worth a dime.";
        

        I haven't seen your method in use, but I've seen the hack.

        This closure idiom is useful and used in all manner of situations.

        { my $static_data; # will persist between calls and IS PRIVATE sub do_stuff { my ( $arg1, $arg2, $reset ) = @_; # first set our static data if we have not been called before # if we have been called then $static_data will be defined # static_data can not be accessed outside of this block - ie s +ub $static_data = _expensive_or_private_init() if $reset or ! def +ined $static_data; # blah } }

        Besides the more obvious private variable usage it works well when you create complex data structures or expensive calls to a DB that you only want to do once

        cheers

        tachyon

        s&&rsenoyhcatreve&&&s&n.+t&"$'$`$\"$\&"&ee&&y&srve&&d&&print

Re: Re: Package-Level Variables
by Anonymous Monk on Jul 28, 2003 at 17:54 UTC
    I didn't quite follow the discussion about whether package or use is more analogous to #include. I had thought there wasn't really a clear analogue to package in C. But aside from that, this was extraordinarily helpful. Thank you very much!