Let me first say that I was once like you are, I was obsessed with trying to make Perl OO be more like other, "stricter" OO systems. I even wrote and released a module to CPAN (see Devel::StrictObjectHash) to do exactly what you are doing here (I used tied hashes though, instead of closures). I also wrote many "protected" and "private" methods which died if the wrong person touched them.

And then, after a few years of this, I realized that never once did I ever actually need any of this code (and the computational overhead that came with it). You see, I realized that I had just built in a bunch of checks, which would always return false, and never execute, because I always used my modules correctly. I then also realized that all my co-workers who used my code did the same. And I would venture to guess that any of the users of my CPAN modules, they also used them correctly. And why do I think this is so?

Because that is how I documented them, plain and simple.

I basically came to the realization, that this is a social problem, and not one to be solved with code. If my co-worker is violating my encapsulation, he/she is wrong. If they have to violate my encapsulation to make things work, then my design is wrong.


Now, from a purely code point of view, I also noticed something about your code (which was always in my code too), especially in how you deal with private and protected methods. You suggest that adding this at the begining of your code for a private method:

caller(0) eq __PACKAGE__ || confess "setQuackBehaviour is private" +;
and this for protected methods:
caller(0)->isa(__PACKAGE__) || confess "setQuackBehaviour is prote +cted";
Both of these methods ignore the possibility that an ancestor class might implement a public version of setQuackBehaviour. Now, my Java is a little rusty, so I don't recall if that is even possible in Java, but that matters not since you are not explicitly disallowing that behavior here anyway.

To properly implement public/private/protected methods, you need to have access to Perl's method dispatcher itself, and that is, I'm sure, not possible without patching perl itself. And to really implement this kind of behavior effectively and efficiently, you probably need some degree of program analysis and code fiddling/generation, which again means a patch to perl. And by the time you are all done with this, you might as well have just saved yourself the time and used Java/C#/C++ or some other language where you get his for free.

-stvn

In reply to Re: Closure objects with public, private, and protected fields by stvn
in thread Closure objects with public, private, and protected fields by gargle

Title:
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, details, 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, summary, 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.