Case-insensitive, lookaround, variable replacement!

Any questions involving matching text strings to patterns - the pattern is called a "regular expression."

Moderator: General Moderators

Post Reply
CobraCards
Forum Newbie
Posts: 13
Joined: Fri Feb 03, 2006 1:40 pm

Case-insensitive, lookaround, variable replacement!

Post by CobraCards »

I need to look take a long text string and replace certain smaller strings within it. Specific requirements:

1) The strings to match need to be passed as variables.

2) Matches should look ahead (and behind) to non-alphabetical characters. (The point being to prevent matches within a word -- e.g., I don't want "sting" to match "interesting.")

3) I need this to be case-INsensitive.


I've discovered ways of doing each of these things individually, but for some reason I can't get them to work together. For example, I can only manage to get case-insensitive results with eregi_replace, but I can only get the lookaround to work with preg_replace.

How can I do all these things at once? :)
User avatar
feyd
Neighborhood Spidermoddy
Posts: 31559
Joined: Mon Mar 29, 2004 3:24 pm
Location: Bothell, Washington, USA

Post by feyd »

so what's the question?

fyi, preg_replace can do case-insensitive: i modifer.
User avatar
feyd
Neighborhood Spidermoddy
Posts: 31559
Joined: Mon Mar 29, 2004 3:24 pm
Location: Bothell, Washington, USA

Post by feyd »

we're going to need more information. Like excerpts of the text, both the text you're trying to find and example strings to best understand.
CobraCards
Forum Newbie
Posts: 13
Joined: Fri Feb 03, 2006 1:40 pm

Post by CobraCards »

To give the background, this code will be used to search messages posted to my trading card game forums, and turn all card titles (a few thousand possibilities, the full list is pulled from a database) into links to that card's image and text.

In the code I'm currently using, the line that does the replacement looks something like this:

Code: Select all

$message = str_replace($match, $link, $message)
$match is an array containing all the cardnames in order, and $link is an array containing the same card names, surrounded by the code that makes them links.

This works OK, but could be better. For example, take the following pair of sentences -- the matches I want are bolded.
"i prefer using sting in this deck, as it has shown some great results in playtesting"
"Sting rules!"

The current code would find only one match as follows. (To correct this, I'd need to make it case-insensitive.)
"i prefer using sting in this deck, as it has shown some great results in playtesting"
"Sting rules!"

But, once I do that, I get too many matches:
"i prefer using sting in this deck, as it has shown some great results in playtesting"
"Sting rules!"

So now, I need to prevent it from matching partial words. (Checking the characters before and after the match seemed the logical way to do this, please let me know if there's a better approach!)

Just to clarify, I know how to put together a regex that would match "Sting" as described above, but when I replace that word with the variable $match (remember that "Sting" is one of a few thousand card titles that need to be checked!) I can't make it work.
User avatar
feyd
Neighborhood Spidermoddy
Posts: 31559
Joined: Mon Mar 29, 2004 3:24 pm
Location: Bothell, Washington, USA

Post by feyd »

Code: Select all

function quoted($a) {
  return preg_quote($a,'#');
}
$match = implode('|',array_map('quoted',array_map('trim',$match)));
$string = preg_replace('#(?<![a-z0-9])('.$match.')(?![a-z0-9])#','<b>\\1</b>',$string);
try that.
CobraCards
Forum Newbie
Posts: 13
Joined: Fri Feb 03, 2006 1:40 pm

Post by CobraCards »

Cool, thanks... I wasn't able to plug that in directly, but looking at your regex led me to the answer I needed. :)

I ran into one more hurdle, will start a new thread for it though.
User avatar
raghavan20
DevNet Resident
Posts: 1451
Joined: Sat Jun 11, 2005 6:57 am
Location: London, UK
Contact:

Post by raghavan20 »

why this kind of simple thing would not work?

Code: Select all

$regex = "#\b".$match[someIndex]."\b#i"; // $match[someIndex] should be your match word like sting...
I am actually unable to understand when you say matching bold strings... :roll:
Post Reply