Praveen Dharmaraj has asked for the wisdom of the Perl Monks concerning the following question:

Hello all, I'm facing a problem here. I am assigning a few regex to a few variables and using them to match inside a loop. Somehow the matching doesn't happen properly. Variables:
$reg1 = /\=/i; $reg2 = /\S+\=\S+/i; $reg3 = /extern.+\b$ur\b\s*/i; $reg4 = /;$/i; $reg5 = /.+\b$ur\b\s*/i; The value of $ur is "rba_Reset_Request".
Iam trying to match this line :
extern void rba_Reset_Request(rba_Reset_Grp_ten dResetGrp_en, rba_Reset_Id_ten dResetIdentifier_en, uint32 dUserDefined_u32);
Can somebody help?

Replies are listed 'Best First'.
Re: Using regex with a variable
by Athanasius (Archbishop) on Mar 14, 2016 at 07:48 UTC

    Hello Praveen Dharmaraj,

    Please put <code> ... </code> tags around your code, to make it readable. See Markup in the Monastery.

    You don’t say how and where the line should match. Please show the output you want to get, together with the value of the $ur variable.

    When storing a regular expression in a variable, you should use Perl’s special qr operator, explained in perlop#Regexp Quote-Like Operators. For example:

    my $reg1 = qr/=/i;

    (No need to escape the = character here, BTW.) And you do use strict; and use warnings;, don’t you?

    Hope that helps,

    Athanasius <°(((><contra mundum Iustus alius egestas vitae, eros Piratica,

Re: Using regex with a variable
by Discipulus (Canon) on Mar 14, 2016 at 07:52 UTC
    Hello Praveen Dharmaraj

    please first of all reformat your question (edit) addig code tags around your code. See Markup in the Monastery

    Second, to store a regex into a variable you need the qr operator; you'll find in the Quote and quote like operator part of perlop

    ps as always someone burned me on the time.. so i add a little example.. ;=)

    perl -e "$regex = qr/=/; print ref $regex,' ',$regex" Regexp (?^:=)

    and see also: /o is dead, long live qr//!

    L*

    There are no rules, there are no thumbs..
    Reinvent the wheel, then learn The Wheel; may be one day you reinvent one of THE WHEELS.

      First of all, sorry for the messy formatting. I am new here. Thanks to you both, using "qr" worked.

      But thing is, I used these variables to reduce the time taken to match. Initially it used to take abt 30 minutes. After using variables, it takes only 10-15 sec. Now after using "qr", it again is taking longer time to match. Reducing the time is my main motto here. This variable problem came up when trying to reduce time.

      Any suggestions ??

        ++ for reformatting your code..

        Now i see that $ur is declared after the regexes.. what your code is supposed to do? if you just put qr in the meanwhile $ur is uundefined and probably is not ywhat you want.. are you using strict and warnings? probably we need more informations about your intention and your possible data inputs.

        L*

        There are no rules, there are no thumbs..
        Reinvent the wheel, then learn The Wheel; may be one day you reinvent one of THE WHEELS.
Re: Using regex with a variable
by BillKSmith (Monsignor) on Mar 14, 2016 at 14:37 UTC

    It appears that you want to search a "C" program for the declaration of the variable specified by $ur. Before you even consider regular expressions, you should look for a module to do this, especially if you have to parse the declaration after you find it.

    I can offer a few comments on the regexes you have shown.

    You are matching a multi-line string. They probably all should use both the /m and /s modifiers.

    $reg1 and $reg2 are largely redundant. Any string that fails 1 will also fail 2. Any string that matches 2 will also match 1.

    In your example, $reg3 and $reg5 match exactly the same thing.

    Variables declared with qr can potentially speed your program if they are declared outside the loop where they are used because they are only complied once.

    Bill
Re: Using regex with a variable
by Marshall (Canon) on Mar 17, 2016 at 02:42 UTC
    As many Monks have said, it is not possible for us to provide excellent help if you don't tell us what you are trying to accomplish. Dumb your example down and remove any proprietary stuff from it. But we need to know what the code below the if statements are doing.

    I probably made some mistakes below, but central to the OP question is "what do you want to accomplish?".

    A simple optimization would be to run all 5 regexes on each line, save the results and use those results in the "if" statements. For example, regex 4 is run repeatedly for each and every "if" statement. my $ends_in_semicolon is a simple scalar that could be tested very quickly.

    The value of $ur is "rba_Reset_Request". foreach my $ur (@strings_to_be_matched) { $reg1 = qr/\=/i; #line has a single '=' #/i makes no difference, delete +that! #there is no "capital ="! $reg2 = qr/\S+\=\S+/i; #line has a single "=" with some +thing #to the left and something to th +e right $reg3 = qr/extern.+\b$ur\b\s*/i; #line has extern rba_Reset_Reque +st $reg4 = qr/;$/i; #line ends in ";" # in C code you are not allowing for t +he #idea that whitespace may be after the + ";" # /;\s*$/; $reg5 = qr/.+\b$ur\b\s*/i; #line has rba_Reset_Request #could just be: #/\b$ur\b/; ? foreach my $line (@contents_of_file) { if(($ln =~ $reg3 and $ln =~ $reg4)){ <some code> # line contains: extern rba_Reset_Request # and ends in a ; } if(($ln =~ $reg5 and $ln=~ $reg4 and ($ln !~ $reg1 or $ln =~ $reg +2)) { # line contains rba_Reset_Request, ends in a ";", has an "=" sign +. <some code> } if(($ln =~ $reg3 and $ln !~ $reg4)){ # line contains extern rba_Reset_Request and doesn't end in ; <some code> } if(($ln =~ $reg5 and $ln !~ $reg4 and $ln !~ $reg1)) #line contains rba_Reset_Request doesn't end in ; or # have an = sign { <some code> } } }