I am not sure i agree with the comment about not using the value of ref().

Granted there are many issues and complexities to the current implementation of references that make me cringe at times. But given that currently there are more than one "type" of reference available (blessed objects aside for a moment), I see ref() as a reasonable way to query that type (albeit somewhat ugly). Of course its use should be highly restricted and very well documented.

Since Perl does not (yet) perform automatic dereferencing (like say Javascript which handles all the "is it a value, is it a ref" stuff for you). And the accessing of hash and array elements are done with different brackets (again, JS allows both to be accessed with the same square bracket syntax). I think that sometimes just knowing a variable is a reference is not enough.

Now, as for usage, my feeling is that ref() should really only be used for checking subroutine arguments. This should always be very well documented, so that its obvious to the user of your module when and where they are allowed to use references. For instance I have a Collection class, which aims to provide a more OO array-like interface (sort of like the Java and Smalltalk collection classes). It can take either an plain perl array or an array reference. The array reference is more efficient (especially when that is what you have already) since it spares the overhead of passing several arguments and the creation of a new array to hold them. I avoid the problem brought up by Ovid (where the first element of a list is itself an array reference) by only allowing a single array reference to be passed:

if (scalar @args == 1) { # .. got an array ref } else { # treat it as a plain array }

I also do the same for my Dictionary class (a hash wrapper) with hash refs and hashes in the argument list.

All other usages of ref() are suspect, but as always if you can justify your reasoning in a good comment, and make sure that you are not causing more problems than you are solving, by all means use it.

All that ref() stuff said, I highly disagree with that usage of UNIVERSAL::isa.

UNIVERSAL is Perl's attempt at a base object class, which like references is maybe not so good an implementation of it. But one of the fundemental base concepts of OO is that of encapsulation, and that usage (and the importation of isa as suggested in the documentation) violates that concept totally.

As for all the thoughts about accepting other types of classes (some which might overload @{} or something similar), this should be detailed in the documentation, and handled approriately. Something like this could be possible.

if (ref($date) =~ /^ARRAY$/) { # ... its an array ref } elsif (ref($date) =~ /ARRAY/) { # ... its an array based class } elsif (overload::Overloaded($date)) { # ... although not definitive, # its possible that @{} is overloaded # use this at your own risk } else { # its probably a string .... }

Of course, I cannot stress documentation enough, it will clear up all the ambiguities of usage.

-stvn

In reply to Re: Is "ref $date eq 'ARRAY'" wrong? by stvn
in thread Is "ref $date eq 'ARRAY'" wrong? by bronto

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.