n.b. blahblah and ikegami and me had a long conversation about his real problem on the chatterbox, earlier today, and we found several entirely different approaches to achieve what he really wants — ikegami even provided a complete alternative program. So, just for the annals, here's a little reply that is just taking the direction of his question here.

I now know you want to distinguish between data matching one of two kinds of sources, it either equals this hash key string (if it's supposed to be treated as a string) or matches the regexp (if it represents a regexp) — the above hash is a kind of dispatch table, originally just matching literal strings, and now he has to extend it to match using a pattern — preferably in a backward compatible way. But you can't distinguish between strings and regexes in hash keys any more, since every hash key is nothing but a string.

One approach I prosposed is to always use a regexp for the hash keys, converting strings to a regexp using quotemeta and string start/end anchors. That way you don't have to make the distinction. But that involves recompiling the regex every time you want to do a test. Not so good.

So another approach is to have an extra caching hash, that maps these string keys to, well, whatever you like. I suggest you use something looking like globs on the left, because it's probably easier for maintenance, eventually converting them to the equivalent regexp by code — once.

my %process = ( 'foo*' => qr/^foo.*$/, foo => 'foo' );
Now you can make the distinction you asked about, in the values of this hash. And regexps remain Regexps.

As a sample converter of glob to regexp, you can do something like this:

{ my %replace; sub glob_to_regexp { my $pattern = shift; %replace or %replace = ( '*' => '.*', '?' => '.' ); $pattern =~ s/(\W)/ $replace{$1} || quotemeta($1)/ge; return qr/^$pattern\z/; } }

Of course, you can implement more advanced glob features if you like, patching the convertor code accordingly.


In reply to Re: Compiled regex as hash key vs. string? by bart
in thread Compiled regex as hash key vs. string? by blahblah

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.