我有一个带有颜色名称的字符串,以逗号或|分隔字符:
$s = 'Blue | Red (light, dark) | Green, Yellow, Brown';
我需要将其转换为数组:
$colors = preg_split('![\|,]!', $s);
但结果是:
Array
(
[0] => Blue
[1] => Red (light
[2] => dark)
[3] => Green
[4] => Yellow
[5] => Brown
)
用逗号分隔“浅,暗”字符串。我想用括号内的逗号分隔。期望的结果:
Array
(
[0] => Blue
[1] => Red (light, dark)
[2] => Green
[3] => Yellow
[4] => Brown
)
我该如何解决?
答案 0 :(得分:2)
$str = 'Blue | Red (light, dark) | Green, Yellow, Brown (light | bright)';
$res = preg_split('/
( # group 1
[^|,]* # 0 or more not pipe or comma
\( # open parenthesis
[^()]* # 0 or more not parenthesis
\) # close parenthesis
) # end group 1
| # OR
[|,] # a pipe or a comma
/x',
$str, -1,
PREG_SPLIT_NO_EMPTY
| PREG_SPLIT_DELIM_CAPTURE);
print_r($res);
<强>输出:强>
Array
(
[0] => Blue
[1] => Red (light, dark)
[2] =>
[3] => Green
[4] => Yellow
[5] => Brown (light | bright)
)
答案 1 :(得分:1)
您需要在替换之前屏蔽输入字符串的括号部分:
$s = 'Blue | Red (light, dark) | Green, Yellow, Brown';
// Mask the parenthesed sections.
// Replace the ',' character with a unique string which you can guarantee will not occur (here: '===')
$sr =
preg_replace_callback(
'!\([^\)]+\)!'
, function ( $p_hit ) { return str_replace(',', '===', $p_hit[0]); }
, $s
);
// original split
$colors = preg_split('![\|,]!', $sr);
// undo masking
$colors = array_map (
function ($elem) { return str_replace('===', ',', $elem); }
, $colors
);
// Print result
print_r ($colors);
输出:
Array
(
[0] => Blue
[1] => Red (light, dark)
[2] => Green
[3] => Yellow
[4] => Brown
)
注意强>
此解决方案不适用于包含嵌套括号的源字符串。
答案 2 :(得分:0)
您只需要使用(*SKIP)(*FAIL)
取消括号内的分隔符。我还在分隔符之前和之后添加了零个或多个空格,以便修剪输出值。
代码:(Demo)
$s = 'Blue | Red (light, dark) | Green, Yellow, Brown';
$colors = preg_split('/\([^)]+(*SKIP)(*FAIL)|\s*[,|]\s*/',$s);
var_export($colors);
echo "\n";
$str = 'Blue | Red (light, dark) | Green, Yellow, Brown (light | bright)';
$colors = preg_split('/\([^)]+(*SKIP)(*FAIL)|\s*[,|]\s*/',$str);
var_export($colors);
输出:
array (
0 => 'Blue',
1 => 'Red (light, dark)',
2 => 'Green',
3 => 'Yellow',
4 => 'Brown',
)
array (
0 => 'Blue',
1 => 'Red (light, dark)',
2 => 'Green',
3 => 'Yellow',
4 => 'Brown (light | bright)',
)
为了争论,您可以在样本输入字符串上使用它:
var_export(preg_match_all('/[a-z]+(?: \([^)]+\))?/i',$str,$out)?$out[0]:'fail');
这种情况不区分地匹配颜色,然后可选地包括尾随的括号表达式。相同的输出。