Jump to content

[SOLVED] Replace anything within ' and ' with PCRE


Vinze

Recommended Posts

[quote author=wildteen88 link=topic=119821.msg491081#msg491081 date=1166974426]
Like this:
[code=php:0]$str = "this is a 'string' which is made up of 'characters'";

echo preg_replace("/'(.*?)'/", '_|_|_|_', $str);[/code]
[/quote]

Yeah that's exactly what I did:
[code=php:0]
$i = 0;
$pattern = '[\'(.*?)\']';
while(preg_match($pattern, $parsed)){
$s_quotes[$i] = preg_replace($pattern, '$1', $parsed, 1);
}
[/code]

But somehow there are totally other values than the strings in $s_quotes, so I must be doing something wrong
Link to comment
Share on other sites

In regex speak, there's a huge difference between this, a character class (part of a regex):
[code][\'(.*?)\'][/code]And this, a full regex:
[code]/'(.*?)'/[/code]

You are right (maybe inadvertently) though, PHP's PCRE does allow you to choose your own delimiter, but (and I may be mistaken here) I don't believe you can use the square brackets '[]' as delimeters. In regex, anything in the square brackets is a character class. So to the regex engine,[code][\'(.*?)\'][/code]Says "match one (1) character from the class", so in this case one of '.', ')', or '?'... etc. Backslashes are use for metacharacters that mean special things like new line (\n), tabs (\t), etc. I'll bet that PHP is complaining about two things here.

One, it doesn't know what metacharacter " \' " is. Two, you only have it matching one character, if you don't have '.' or '?' or whatever in the string I'd expect it to fail. wildteen88's solution works great. If you want to store the pattern in a variable (I see this everywhere, I don't know why people always want to do it) store it like this:
[code]$pattern = "/'.*?'/";[/code]
You may want to add the 's' modifier in case you have quoted strings spanning multiple lines.

I (just my opinion/way of doing it) would do something like this:
[code]$str = "this is a 'string' which is made up of 'characters'";

echo preg_replace("/'[^']+'/", '_|_|_|_', $str);[/code]
I've gotten into trouble occasionally using '.*?' too much. Although wildteen88's solution works great too.
Link to comment
Share on other sites

[quote author=c4onastick link=topic=119821.msg494254#msg494254 date=1167584322]
In regex speak, there's a huge difference between this, a character class (part of a regex):
[code][\'(.*?)\'][/code]And this, a full regex:
[code]/'(.*?)'/[/code]

You are right (maybe inadvertently) though, PHP's PCRE does allow you to choose your own delimiter, but (and I may be mistaken here) I don't believe you can use the square brackets '[]' as delimeters. In regex, anything in the square brackets is a character class. So to the regex engine,[code][\'(.*?)\'][/code]Says "match one (1) character from the class", so in this case one of '.', ')', or '?'... etc. Backslashes are use for metacharacters that mean special things like new line (\n), tabs (\t), etc. I'll bet that PHP is complaining about two things here.

One, it doesn't know what metacharacter " \' " is. Two, you only have it matching one character, if you don't have '.' or '?' or whatever in the string I'd expect it to fail. wildteen88's solution works great. If you want to store the pattern in a variable (I see this everywhere, I don't know why people always want to do it) store it like this:
[code]$pattern = "/'.*?'/";[/code]
You may want to add the 's' modifier in case you have quoted strings spanning multiple lines.

I (just my opinion/way of doing it) would do something like this:
[code]$str = "this is a 'string' which is made up of 'characters'";

echo preg_replace("/'[^']+'/", '_|_|_|_', $str);[/code]
I've gotten into trouble occasionally using '.*?' too much. Although wildteen88's solution works great too.
[/quote]

[ and ] work great at all my other regular expressions, so they cannot be the problem. Also, I defined the pattern within ' and ', that's why I added the backslashes (so they will be parsed for the regex as a normal ').

But I'm starting to think the problem is somewhere in $str which is a bunch of PHP code that needs to be automatically cleaned up.
Link to comment
Share on other sites

[quote author=Vinze link=topic=119821.msg494258#msg494258 date=1167584757]
[ and ] work great at all my other regular expressions, so they cannot be the problem. Also, I defined the pattern within ' and ', that's why I added the backslashes (so they will be parsed for the regex as a normal ').

But I'm starting to think the problem is somewhere in $str which is a bunch of PHP code that needs to be automatically cleaned up.
[/quote]

Good to know, I wondered about that, I've never used [ and ] for anything other than character classes, I learned something today! With out seeing some of the code that's going into $str, really the only thing I would suggest is to add the 's' modifier to your pattern so that the dot picks up newlines too. Is the error that preg_replace throws any help? Or is there just no match?
Link to comment
Share on other sites

[quote author=c4onastick link=topic=119821.msg494493#msg494493 date=1167622794]
[quote author=Vinze link=topic=119821.msg494258#msg494258 date=1167584757]
[ and ] work great at all my other regular expressions, so they cannot be the problem. Also, I defined the pattern within ' and ', that's why I added the backslashes (so they will be parsed for the regex as a normal ').

But I'm starting to think the problem is somewhere in $str which is a bunch of PHP code that needs to be automatically cleaned up.
[/quote]

Good to know, I wondered about that, I've never used [ and ] for anything other than character classes, I learned something today! With out seeing some of the code that's going into $str, really the only thing I would suggest is to add the 's' modifier to your pattern so that the dot picks up newlines too. Is the error that preg_replace throws any help? Or is there just no match?
[/quote]

The "s" modifier did not help unfortunately. I haven't looked at it yet but there is no error message, just no match.
Link to comment
Share on other sites

[quote author=Vinze link=topic=119821.msg491082#msg491082 date=1166974786]
Yeah that's exactly what I did:
[code=php:0]
$i = 0;
$pattern = '[\'(.*?)\']';
while(preg_match($pattern, $parsed)){
$s_quotes[$i] = preg_replace($pattern, '$1', $parsed, 1);
}
[/code]
But somehow there are totally other values than the strings in $s_quotes, so I must be doing something wrong
[/quote]

[tt]preg_replace [/tt]does not modify[tt] $parsed[/tt], resulting in an infinite loop. How about this?

[code=php:0]
<?php
$str = "this is a 'string' which is made up of 'characters'";
$pattern = '[\'(.*?)\']';
preg_match_all($pattern, $str, $matches);
echo '<pre>', print_r($matches, true), '</pre>';
?>
[/code]
Link to comment
Share on other sites

[quote author=effigy link=topic=119821.msg495479#msg495479 date=1167762452]
[quote author=Vinze link=topic=119821.msg491082#msg491082 date=1166974786]
Yeah that's exactly what I did:
[code=php:0]
$i = 0;
$pattern = '[\'(.*?)\']';
while(preg_match($pattern, $parsed)){
$s_quotes[$i] = preg_replace($pattern, '$1', $parsed, 1);
}
[/code]
But somehow there are totally other values than the strings in $s_quotes, so I must be doing something wrong
[/quote]

[tt]preg_replace [/tt]does not modify[tt] $parsed[/tt], resulting in an infinite loop. How about this?

[code=php:0]
<?php
$str = "this is a 'string' which is made up of 'characters'";
$pattern = '[\'(.*?)\']';
preg_match_all($pattern, $str, $matches);
echo '<pre>', print_r($matches, true), '</pre>';
?>
[/code]
[/quote]
Ah, sorry, I put down the code I remembered by heart as at the time I did not have it within reach. This is the full code which should not have that problem:
[code=php:0]$s_pattern = '[\'(.*?)\']';
$i = 0;
while(preg_match($s_pattern, $parsed)){
$s_quotes[$i] = preg_replace($s_pattern, '$1', $parsed, 1);
$parsed = preg_replace($s_pattern, '_|_|_|_', $parsed, 1);
$i++;
}[/code]

But using preg_match_all () also is an option, I'll try that and you never know, it might all of a sudden work :D
Link to comment
Share on other sites

For the record, you do not need to use[tt] $i[/tt]: empty square brackets will result in a push to the array. Also, your code works, but not in the way you may expect. Examine this with the echo statement for debugging:

[code=php:0]
<?php
$parsed = "'a' string with 'single' quotes";
$s_pattern = '[\'(.*?)\']';
while(preg_match($s_pattern, $parsed)){
$s_quotes[] = preg_replace($s_pattern, '$1', $parsed, 1);
$parsed = preg_replace($s_pattern, '_|_|_|_', $parsed, 1);
echo '<hr><pre>', print_r($s_quotes, true), $parsed, '</pre>';
}
?>
[/code]
Link to comment
Share on other sites

[quote author=effigy link=topic=119821.msg496087#msg496087 date=1167835355]
For the record, you do not need to use[tt] $i[/tt]: empty square brackets will result in a push to the array. Also, your code works, but not in the way you may expect. Examine this with the echo statement for debugging:

[code=php:0]
<?php
$parsed = "'a' string with 'single' quotes";
$s_pattern = '[\'(.*?)\']';
while(preg_match($s_pattern, $parsed)){
$s_quotes[] = preg_replace($s_pattern, '$1', $parsed, 1);
$parsed = preg_replace($s_pattern, '_|_|_|_', $parsed, 1);
echo '<hr><pre>', print_r($s_quotes, true), $parsed, '</pre>';
}
?>
[/code]
[/quote]

I knew about the empty brackets but do not use them often as sometimes I want to do something else later on and then the array key is incremented without me wanting that.

Anyway, my code did not work, preg_match_all() did and I had already tried it with "blabla' bla ' " and that worked out great too :D
Link to comment
Share on other sites

[quote author=effigy link=topic=119821.msg496087#msg496087 date=1167835355]
For the record, you do not need to use[tt] $i[/tt]: empty square brackets will result in a push to the array. Also, your code works, but not in the way you may expect. Examine this with the echo statement for debugging:

[code=php:0]
<?php
$parsed = "'a' string with 'single' quotes";
$s_pattern = '[\'(.*?)\']';
while(preg_match($s_pattern, $parsed)){
$s_quotes[] = preg_replace($s_pattern, '$1', $parsed, 1);
$parsed = preg_replace($s_pattern, '_|_|_|_', $parsed, 1);
echo '<hr><pre>', print_r($s_quotes, true), $parsed, '</pre>';
}
?>
[/code]
[/quote]

Crap. I had tested it with a double-quoted string that contained a single quote, but I had to test with with [i]two[/i] quotes, and then it does not work :(
Link to comment
Share on other sites

[quote author=effigy link=topic=119821.msg496275#msg496275 date=1167848768]
I'm confused by your response. It [i]should not[/i] work with less than 2 single quotes, and it [i]should[/i] work with 2 or more single quotes.
[/quote]

When my code contains [code=php:0]echo "blabla 'single quotes' blabla ";[/code] then it won't work :(
Link to comment
Share on other sites

If I change [code=php:0]$parsed = "'a' string with 'single' quotes";[/code] to [code=php:0]$parsed = "blabla 'single quotes' blabla ";[/code] it works fine. If you want[tt] echo "blabla 'single quotes' blabla "; [/tt]within the string, it stills works if you escape the double quotes.
Link to comment
Share on other sites

[quote author=effigy link=topic=119821.msg496880#msg496880 date=1167927860]
If I change [code=php:0]$parsed = "'a' string with 'single' quotes";[/code] to [code=php:0]$parsed = "blabla 'single quotes' blabla ";[/code] it works fine. If you want[tt] echo "blabla 'single quotes' blabla "; [/tt]within the string, it stills works if you escape the double quotes.
[/quote]

When it starts parsing the code, it first replaces all occurences of single-quoted strings with _|_|_|_ and saves the previous values in an array, then it replaces all occurences of double-quoted strings with -|-|-|- and saves the old values in an array, then it indents all the code and then puts the strings back in place. However, now I end up with [code=php:0]"blabla _|_|_|_ blabla "[/code] instead of [code=php:0]"blabla 'single quotes' blabla "[/code]
Link to comment
Share on other sites

[quote author=effigy link=topic=119821.msg497126#msg497126 date=1167955700]
Can you show some code and the expected result? I didn't know you were using another pattern for doubles.
[/quote]

Good point. I now use the same pattern for single and double quotes, and now it works. However, when there is just one quote it will insert a line-break but surely I'll be able to solve that. Thanks!
Link to comment
Share on other sites

This thread is more than a year old. Please don't revive it unless you have something important to add.

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

×
×
  • Create New...

Important Information

We have placed cookies on your device to help make this website better. You can adjust your cookie settings, otherwise we'll assume you're okay to continue.