Beefy Boxes and Bandwidth Generously Provided by pair Networks
Welcome to the Monastery
 
PerlMonks  

Troubles with m!(??{substr(...)})!

by jens (Pilgrim)
on Nov 20, 2002 at 08:23 UTC ( #214373=perlquestion: print w/ replies, xml ) Need Help??
jens has asked for the wisdom of the Perl Monks concerning the following question:

After lengthly and ultimately fruitless discussion in the CB, here's a poser for you:

I want to join the following two lines:

#$url = substr($test, 0, $_); #if ($test =~ /$url/ {

and get rid of the temp variable doing fancy footwork like so....

if ($test =~ m#(??{substr($test, 0, $_)})#) {
The error I get is
Argument $test isn't numeric in substr at (re_eval 1) l
Any ideas on this one?
--
Microsoft delendum est.

Comment on Troubles with m!(??{substr(...)})!
Select or Download Code
Re: Troubles with m!(??{substr(...)})!
by Enlil (Parson) on Nov 20, 2002 at 09:53 UTC
    I think the answer lies in that $_ is set to $test inside the regular expression statement, so it is not a numerical argument unless $test is numerical. As proof (as I was curious to find out what was going on I tried a couple of things to come to a conclusion)

    1. When I changed the $_ to a numerical value inside the regex instead:

    if ($test =~m#(??{substr($test, 0, 8)})#) { }
    and the regex will work, without warning.

    2. When I set the string $test to a something numerical (12,444.343,etc.) and again it will work without warning.

    3. I tried setting $_ to a number outside and again it failed.

    use strict; use warnings; my $test = "fee fi fo fee"; $_++; if ($test =~ m!((??{ substr($test,0,$_) }))!) { };
    So what I figured it dealt with the $_ So what I finally did was the following as final proof that I was on the right track:
    use strict; use warnings; my $test = "fee fi fo free"; if ($test =~ m!((??{ print "$_\n";substr($test,0,$_) }))!) { };
    Which when it runs displays the following:
    fee fi fo free Argument "fee fi fo free" isn't numeric in substr at (re_eval 1) line +1.
    -enlil

      As one who was puzzled by this in cb, I was happy to see this sensible explanation. I really thought you'd found the answer, but this one-liner seems to say not: perl -e'($foo="bar") =~ m/($_)/;print $1,$/'

      Update: ++ Enlil and BrowserUK for figuring this out! It's not m// but (??{}) that does it.

      That's a fact worth knowing, and props for curiosity over efficiency! A modest application:

      sub isPalindrome { $_[0] =~ /(??{quotemeta scalar reverse $_})/i } sub isAllUpper { $_[0] =~ /(??{uc})/ }

      After Compline,
      Zaxo

        I started playing with the perl debugger and I still think I am right though I do not quite know the reasoning behind it. The debugging went as follows ( I am omitting much, but leaving the important parts). First the program:
        use strict; use warnings; my $test = "fee fi fo free"; if ($test =~ m!((??{ substr($test,0,$_) }))!) {};
        Now the debugging stuff:
        DB<1> V main # $_ never appears after this command DB<2> s main::(bah4.pl:6): if ($test =~ m!((??{ substr($test,0,$_) }))!) +{}; DB<2> V main # $_ never appears after this command DB<3> s main::((reeval 2)[bah4.pl:6]:1): DB<3> V main #At this point again variables in main are #listed there is a line: # $_ = 'fee fi fo free' DB<4> s Argument "fee fi fo free" isn't numeric in substr at (reeval 2)[bah4.p +l:6] line 1.
        and then a bunch of error stuff. I ran the one liner through the debugger and $_ never gets set, but as I mentioned before I do not know why the difference, perchance one of the many wiser monks than I might enlighten us at this point.

        -enlil

        *Note: I have not used the debugger all the much, so if I managed to confuse myself and thereby gave out misinformation let me know.

Re: Troubles with m!(??{substr(...)})!
by UnderMine (Friar) on Nov 20, 2002 at 10:02 UTC
    Can we have some sample data that you are trying to evaluate?

    What happens if you don't use $_ as this may be getting corrupted durring the evaluation

    Hope it helps
    UnderMine

Re: Troubles with m!(??{substr(...)})!
by grinder (Bishop) on Nov 20, 2002 at 13:36 UTC

    Without trying to sound facetious... Why would you want to do a thing like that?

    I can't figure out the purpose. It seems to me as if you are taking a leading substring from a string, and then seeing if you match the substring in the string. Which you always will, unless the substring happens to contain meta-characters which will be interpreted differently by the regexp engine.

    So if that is the case, why don't you just see whether

    substr($test, 0, $_) eq quotemeta(substr($test), 0, $_))

    Of course, I may be overlooking something obvious, so feel free to clue me in.


    print@_{sort keys %_},$/if%_=split//,'= & *a?b:e\f/h^h!j+n,o@o;r$s-t%t#u'
Re: Troubles with m!(??{substr(...)})!
by BrowserUk (Pope) on Nov 20, 2002 at 13:37 UTC

    I'm slightly confused by your goal? I assume that this is intended to be used inside a loop with $_ as the loop var, so when I saw Enlil's conclusions that m// is messing with $_ I thought why not avoid m// and use index and came up with this.

    if( 1+index($test,substr($test,0,$_)) ){ # Do stuff }

    looked like it would do the same test as your 2 steps, but then I realised that what this translates to is

     if( $test contains a substring of $test )...

    which by definition, will always be true!

    Did I miss something?


    Okay you lot, get your wings on the left, halos on the right. It's one size fits all, and "No!", you can't have a different color.
    Pick up your cloud down the end and "Yes" if you get allocated a grey one they are a bit damp under foot, but someone has to get them.
    Get used to the wings fast cos its an 8 hour day...unless the Govenor calls for a cyclone or hurricane, in which case 16 hour shifts are mandatory.
    Just be grateful that you arrived just as the tornado season finished. Them buggers are real work.

Re: Troubles with m!(??{substr(...)})!
by BUU (Prior) on Nov 21, 2002 at 01:57 UTC
    In conclusion and after much consulting, taking the following code:
    #$url = substr($test, 0, $_); #if ($test =~ /$url/ {
    We can easily simplify that to: if(1){ You're welcome.


    (Note: of course now the original poster will post some wacky and zany update involving metachars, and i shall look extremely silly and lose much XP. Damn.)

Log In?
Username:
Password:

What's my password?
Create A New User
Node Status?
node history
Node Type: perlquestion [id://214373]
Approved by fireartist
Front-paged by jarich
help
Chatterbox?
and the web crawler heard nothing...

How do I use this? | Other CB clients
Other Users?
Others taking refuge in the Monastery: (8)
As of 2014-10-02 17:13 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    What is your favourite meta-syntactic variable name?














    Results (66 votes), past polls