I'm having a dumb moment here...

I am trying to search out strings and match user input with what's stored in database.

I'm using

if($data =~ $user_input){then do something;}

It's important to note that all the "$data" strings are all numbers.

So for example, user puts in "1" and it matches "1, 10, 125..."
But the problem is if user inputs "8" it will match "800" but not "1008, 181..."

Can someone help me see what I'm missing here?

Derek

Well, the first thing is to properly construct your regexp:

if($data =~ /$user_input/){then do something;}

assuming $data is the number like 1008 and 800, etc, and $user_input is the number 8 then it would match any string that has the number 8 in it anywhere. You can easily test that:

@nums = qw(800 1008 34 8 99 111118  11111 8111111 111181111);
$user_input = 8;

foreach my $data (@nums) {
   if($data =~ /$user_input/){print "Matched $data\n";}
}

output:

Matched 800
Matched 1008
Matched 8
Matched 111118
Matched 8111111
Matched 111181111

Well, the first thing is to properly construct your regexp:

if($data =~ /$user_input/){then do something;}

assuming $data is the number like 1008 and 800, etc, and $user_input is the number 8 then it would match any string that has the number 8 in it anywhere. You can easily test that:

@nums = qw(800 1008 34 8 99 111118  11111 8111111 111181111);
$user_input = 8;

foreach my $data (@nums) {
   if($data =~ /$user_input/){print "Matched $data\n";}
}

output:

Matched 800
Matched 1008
Matched 8
Matched 111118
Matched 8111111
Matched 111181111

According to PERL documentation, in this instance it is unnecessary to use "//" with the regexp. My understanding is that "=~ $user_input" yields the same as "=~ /$user_input/", which is backed up by doing tests both ways. So no, this is not the problem.

"So for example, user puts in "1" and it matches "1, 10, 125..."
But the problem is if user inputs "8" it will match "800" but not "1008, 181..." "

It only matches 8 in "800", not in "180" or "108". I think it has something to do with numbers...because the same construction used with letters works fine. For example, $user_input=a matches "a, car, blah, cba, cancan".

It will match. I just posted code that proves that. But your correct, it works fine without the // delimiters.

Are you using chomp() on the user input before using it in the regexp?

It will match. I just posted code that proves that. But your correct, it works fine without the // delimiters.

Are you using chomp() on the user input before using it in the regexp?

Kevin, I appreciate your post, but it turns out that the whole problem was my oversite the whole time. I still don't totally understand WHY it wouldn't match, gotta think through that a bit more, but let me try to briefly explain.

The $user_input is a search request from the user (web based) to search a database of financial transactions. In the instance of a check transaction, the data is stored as "Check 1234" indicating both the transaction type and the check number. So when the user inputs a check number ($user_input) of say "8", it searches the data file in that column of data for "8" against the actual data which is "Check 1008" or "Check 1800". Follow? I WAS altering the user data to reflect, in our example, "Check 8" instead of just "8". It was a simple fix, just removed the line that modifies the $user_input variable and now it matches "8" ($user_input) against the data string "Check 1234", and voila! It matches properly. Again, I am not entirely sure why "Check 8" from user input when matched against "Check 800" returns true, but when matched against "Check 1800" returns false.

I hope this hasn't been entirely confusing, and if you understand what I am describing here at all, I would like to hear your insight on this. Long story short, it's fixed now! Thanks!

Derek

If you write the regexp like this:

/Check 8/

it will match that substring inside of any larger string, so "Check 8000" would match, but not "Check 1008" it would also match "PreCheck 811181118" as long as the regexp find "Check 8" anywhere in the string in that exact order it will return true. You may need to use some type of anchor to force the match to match only at specific parts of a string, the beginning or end for example. But on another note "Check 8" is not a pattern its a string or a substring so using index() might be more appropriate.

I would say that you could do something like /Check\s+(\d+)?8/

I believe that would say match Check and a space or more, and one or more optional digits and an 8, and that *should* match anything that's Check 1008 or something like that...

Of course if you are looking for Check only (to exclude PreCheck 811181118 like Kevin was mentioning) you could maybe add \b to the front to denote the beginning of a word then you only look for terms that start with Check?

Onaclov Nation

This article has been dead for over six months. Start a new discussion instead.