【发布时间】:2014-01-07 08:52:18
【问题描述】:
目前我正在尝试在 php 中创建一个函数来扩展带有括号的化学产品/试剂。我的函数仅使用一组括号与产品/试剂一起工作,但由于括号内的 2 个或更多括号或括号连词而失败。
function expand_eq($string) {
while(substr_count($string, "(")>=1 and substr_count($string, ")")>=1) {
$tmpstr01 = preg_replace('/(.*)[(](.+)[)]([0-9]*)(.*)/i', '$1$4', $string);
$tmpstr02 = preg_replace('/(.*)[(](.+)[)]([0-9]*)(.*)/i', '$2', $string);
$tmpstr03 = preg_replace('/(.*)[(](.+)[)]([0-9]*)(.*)/i', '$3', $string);
$tmpstr02 = preg_replace('/([A-Z][a-z]*)([0-9]*)/', '$1$2 ', $tmpstr02);
if(substr($tmpstr02, -1)===" ") {$tmpstr02 = substr($tmpstr02, 0, -1);} //remove last space
$tmpstr02 = explode(" ", $tmpstr02);
for ($j = 0; $j <= count($tmpstr02)-1; $j++) {
if(preg_match_all('/[A-Z][a-z]*[0-9]+$/', $tmpstr02[$j])) {
$tmpstr02[$j] = preg_replace('/([A-Z][a-z]*)([0-9]+)$/', '$1', $tmpstr02[$j]) . preg_replace('/([A-Z][a-z]*)([0-9]+)$/', '$2', $tmpstr02[$j]) * $tmpstr03;
}
else {
$tmpstr02[$j] = $tmpstr02[$j] . $tmpstr03;
}
}
$string = $tmpstr01 . implode($tmpstr02);
}
return $string;
}
示例:
echo expand_eq("(NH4)3");
return: "N3H12" - Correct!
echo expand_eq("(Mo3O10)4");
return "Mo12O40" - Correct!
echo expand_eq("(NH4)3(P(Mo3O10)4)");
return "P4Mo0O0N3H12" - Incorrect! Correct value should be: "N3H12PMo12O40"
echo expand_eq("H((O)2)2");
return "HO44" - Incorrect! Correct value should be: "HO4"
我从一周前开始尝试解决这个问题,但我仍然没有设法解决它。
【问题讨论】:
-
可能是贪心匹配。试试
/iU而不是/i -
感谢您的评论。我测试了将 /iU 添加到正则表达式,但这并没有解决问题。我可能需要重新编写代码......
-
我强烈建议在这里使用堆栈解析器而不是正则表达式。 every ( 推入一个新堆栈,every ) + number 弹出一个堆栈,将整个内容相乘,然后将结果元素重新推入。