Beefy Boxes and Bandwidth Generously Provided by pair Networks
No such thing as a small change

Comment on

( #3333=superdoc: print w/ replies, xml ) Need Help??

I've starting writing more OO code more like:

package My::Class; use vars qw( $VERSION ); BEGIN { $VERSION= 1.001 } package My::Class::_internal; sub My::Class::new { my $self= bless {}, "My::Class::_object"; #... return $self; } sub utilityFunction { my $self= shift @_; # ... } sub My::Class::_object::method { my $self= shift @_; # ... utilityFunction( $self, @args ); # ... }
That is, have only class methods in the My::Class namespace, have only object methods in the My::Class::_object namespace, and put utility function in some other namespace (package). Note that all of the functions are actually compiled in the "internal" package (even though they are named into a different package) so that they can call utility function w/o specifying a package name.

This prevents the module user from making the following mistakes:

# Calling a class method via an object: my $obj2= $obj1->new(); # Calling an object method via the class name: my $ret= My::Class->method() # Using my utility function: $obj->utilityFunction();
Note that this prevents naive inheritance from working. I don't mind much as I think that inheritance should be mostly a last-resort technique and should not be used with a class that wasn't specifically designed to allow inheritance. You can also think of My::Class as a "factory" class, if that makes you feel better (in fact, several of my recent classes really were factory classes).

Of course, you might well want to follow OO Perl tradition (what little there is of it, OO Perl being so young) and allow $obj->new(). One way to do that is by "exporting" sub new:     *My::Class::_object::new= \&My::Class::new;
or you can just not separate your object methods from your class methods, instead just separating your utility functions (note that the utility functions are not methods because calling them as methods just adds overhead in order to search the inheritance heirarchy but you don't want to allow them to be overridden via inheritance so that would just be a waste).

The following example does that and even uses You can also use when you separate everything (like the first example does), and it can be quite nice, especially if you have lots of methods. It is even nicer if you have multiple object types and some methods are shared among multiple object types (yes, you can share methods with less flexibility via inheritance).

package My::Class; use vars qw( $VERSION ); BEGIN { $VERSION= 1.001 } # Following line moved down to increase robustness: ## My::Class::_internal->import( ":DEFAULT" ); package My::Class::_internal; require Exporter; use vars qw( @EXPORT_OK ); BEGIN { *import= \&Exporter::import; @EXPORT_OK= qw( new method ); } sub utilityFunction { my $self= shift @_; # ... } sub new { my $class= shift @_; my $proto; $class= ref( $proto= $class ) if ref $class; my $self= bless {}, $class; #... return $self; } sub method { my $self= shift @_; # ... utilityFunction( $self, @args ); # ... } package My::Class; My::Class::_internal->import( ":DEFAULT" );
Note that there are lots of ways you can deal with getting things to happen in the proper order here. The above commented line would work because it is not in a BEGIN block while "everything" else is. But I show the last two lines instead as they are less sensitive to having something in a BEGIN block that shouldn't be or vice versa.

You can even create a separate My/Class/ file so that a standard

package My::Class; use My::Class::_internal;
would work.

        - tye (but my friends call me "Tye")

In reply to (tye)Re: Private Class Methods by tye
in thread Private Class Methods by dhable

Use:  <p> text here (a paragraph) </p>
and:  <code> code here </code>
to format your post; it's "PerlMonks-approved HTML":

  • Posts are HTML formatted. Put <p> </p> tags around your paragraphs. Put <code> </code> tags around your code and data!
  • Titles consisting of a single word are discouraged, and in most cases are disallowed outright.
  • Read Where should I post X? if you're not absolutely sure you're posting in the right place.
  • Please read these before you post! —
  • Posts may use any of the Perl Monks Approved HTML tags:
    a, abbr, b, big, blockquote, br, caption, center, col, colgroup, dd, del, div, dl, dt, em, font, h1, h2, h3, h4, h5, h6, hr, i, ins, li, ol, p, pre, readmore, small, span, spoiler, strike, strong, sub, sup, table, tbody, td, tfoot, th, thead, tr, tt, u, ul, wbr
  • You may need to use entities for some characters, as follows. (Exception: Within code tags, you can put the characters literally.)
            For:     Use:
    & &amp;
    < &lt;
    > &gt;
    [ &#91;
    ] &#93;
  • Link using PerlMonks shortcuts! What shortcuts can I use for linking?
  • See Writeup Formatting Tips and other pages linked from there for more info.
  • Log In?

    What's my password?
    Create A New User
    and the web crawler heard nothing...

    How do I use this? | Other CB clients
    Other Users?
    Others examining the Monastery: (5)
    As of 2016-02-13 22:25 GMT
    Find Nodes?
      Voting Booth?

      How many photographs, souvenirs, artworks, trophies or other decorative objects are displayed in your home?

      Results (449 votes), past polls