Reputation: 392
Let's suppose I have this string:
this is a "test for stackoverflow", with 'single quotes too' and "combined 'quotes single and double'"
And I need to get:
thisisa"test for stackoverflow",with'single quotes too'and"combined 'quotes single and double'"
This was just an example, but quotes can be nested up to 3 levels (" str ' str " str " ' "), there may be also multiple lines. I need to get a RegEx to replace all the spaces outside quotes.
Upvotes: 0
Views: 1145
Reputation: 11041
Use the following regex:
/(?:"[^"]++"|'[^']++')(*SKIP)(*F)|\s/
Expression explanation:
(?:"[^"]++"|'[^']++')
Matches quotes and everything within the quotes.(*SKIP)(*F)
Skips the pointer to the next position and discard the match.|
OR (The following will only be matched if the above alternative does not discard this already\s
Whitespaces.Upvotes: 0
Reputation: 785058
You can use this regex for this:
$s = <<< EOF
this is a "test for stackoverflow" , with 'single quotes too' and "combined 'quotes single and double'"
EOF;
echo preg_replace('/(?| *(".*?") *| *(\'.*?\') *)| +/s', '$1', $s);
thisisa"test for stackoverflow",with'single quotes too'and"combined 'quotes single and double'"
Upvotes: 3
Reputation: 5857
Probably not the most elegant solution but it's a start (single-apostrophes that aren't meant as a quote aren't supported. Replace those before and replace them back later):
<?PHP
$str = "this is a \"test for stackoverflow\", with 'single quotes too' and \"combined 'quotes single and double'\"";
$cleared = clearString($str);
$solution = "thisisa\"test for stackoverflow\",with'single quotes too'and\"combined 'quotes single and double'\"";
assert($cleared == $solution);
function copyQuote($str, $until, $offset = 0)
{
$p = strpos($str, $until, $offset);
if ($p !== FALSE)
return substr($str, $offset, $p-$offset);
else
throw new Exception("Unclosed Quote Exception at position ".$offset);
}
function clearString($str)
{
$retVal = "";
$len = strlen($str);
for ($i = 0; $i < $len; $i++)
{
if ($str[$i] == "\"" || $str[$i] == "'")
{
$quote = copyQuote($str, $str[$i], $i+1);
$retVal .= $str[$i].$quote.$str[$i];
$i += strlen($quote)+1;
} else {
// Skip whitespaces outside of quotes, add any other check you'd like to do here
if ($str[$i] != " " && $str[$i] != "\t")
{
$retVal .= $str[$i];
}
}
}
return $retVal;
}
?>
Upvotes: -1