处理Javascript正则表达式子匹配
我试图编写一些JavaScript正则表达式,用真正的html标记替换用户输入的标记,因此处理Javascript正则表达式子匹配,javascript,regex,markdown,Javascript,Regex,Markdown,我试图编写一些JavaScript正则表达式,用真正的html标记替换用户输入的标记,因此[b]将变成等等。我使用的正则表达式看起来是这样的 var exptags = /\[(b|u|i|s|center|code){1}]((.){1,}?)\[\/(\1){1}]/ig; 使用以下JavaScript s.replace(exptags,"<$1>$2</$1>"); 但是,如果标记嵌套在彼此内部,它将只匹配外部标记,例如 [b]foo [u]to the[/u
[b]
将变成
等等。我使用的正则表达式看起来是这样的
var exptags = /\[(b|u|i|s|center|code){1}]((.){1,}?)\[\/(\1){1}]/ig;
使用以下JavaScript
s.replace(exptags,"<$1>$2</$1>");
但是,如果标记嵌套在彼此内部,它将只匹配外部标记,例如
[b]foo [u]to the[/u] bar[/b]
这将仅与b
标记匹配。我怎样才能解决这个问题?我应该循环直到起始字符串与结果相同吗?我有一种感觉,(({1,}?
模式也错了
谢谢你不能用正则表达式表达递归 但是,您可以使用平衡匹配使用.NET的System.Text.RegularExpressions来实现这一点。请参阅此处的更多信息: 如果您使用的是.NET,您可能可以通过回调实现所需的功能。 如果没有,您可能需要使用自己的小javascript解析器 同样,如果您有能力访问服务器,您可以使用完整的解析器。:)
你要这个干什么?如果不是为了预览,我强烈建议您在服务器端进行处理。AFAIK您不能用正则表达式表示递归 但是,您可以使用平衡匹配使用.NET的System.Text.RegularExpressions来实现这一点。请参阅此处的更多信息: 如果您使用的是.NET,您可能可以通过回调实现所需的功能。 如果没有,您可能需要使用自己的小javascript解析器 同样,如果您有能力访问服务器,您可以使用完整的解析器。:)
你要这个干什么?如果不是预览,我强烈建议您在服务器端进行处理。是的,您必须循环。或者,由于您的标记看起来非常像HTML标记,您可以分别替换
的[b]
,以及
的[/b]
。(.){1,}? 与(.*)相同-即任何符号,最小可能的序列长度
更新:感谢MrP,(..{1,}?是(+.)+?,我的错。是的,你必须循环。或者,由于您的标记看起来非常像HTML标记,您可以分别替换
的[b]
,以及
的[/b]
。(.){1,}? 与(.*)相同-即任何符号,最小可能的序列长度
更新:感谢MrP,(..{1,}?是(.)+?,我的错。你说得对,内部模式很麻烦
((.){1,}?)
也就是说,至少进行一次捕获匹配,然后捕获整个过程。标记中的每个字符都将被捕获为一个组
当您不需要结束元素名时,您也在捕获它,并且在暗示结束元素名时使用{1}
。以下是清理版本:
/\[(b|u|i|s|center|code)](.+?)\[\/\1]/ig
对另一个问题不确定。您认为内部模式很麻烦,这是对的
((.){1,}?)
也就是说,至少进行一次捕获匹配,然后捕获整个过程。标记中的每个字符都将被捕获为一个组
当您不需要结束元素名时,您也在捕获它,并且在暗示结束元素名时使用{1}
。以下是清理版本:
/\[(b|u|i|s|center|code)](.+?)\[\/\1]/ig
不确定另一个问题。您可以重复应用regexp,直到它不再匹配。这会做一些奇怪的事情,比如“[b][b]foo[/b][b]”=>“[b]foo[/b]”=>“foo”,但就我所见,最终结果仍然是一个带有匹配(尽管不一定正确嵌套)标记的合理字符串
或者,如果您想做到“正确”,只需编写一个简单的递归下降解析器。尽管人们可能希望“[b]foo[u]bar[/b]baz[/u]”能够工作,但这很难用解析器识别。您可以重复应用regexp,直到它不再匹配为止。这会做一些奇怪的事情,比如“[b][b]foo[/b][b]”=>“[b]foo[/b]”=>“foo”,但就我所见,最终结果仍然是一个带有匹配(尽管不一定正确嵌套)标记的合理字符串
或者,如果您想做到“正确”,只需编写一个简单的递归下降解析器。尽管人们可能期望“[b]foo[u]bar[/b]baz[/u]”起作用,但这很难用解析器来识别。嵌套块没有被替换的原因是因为[b]的匹配将位置放在[/b]之后。因此,(..{1,}?)匹配的所有内容都将被忽略 可以在服务器端编写递归解析器——Perl使用,Ruby可能也有类似的功能 不过,您不一定需要真正的递归。您可以使用相对简单的循环来等效地处理字符串:
var s = '[b]hello[/b] [u]world[/u] [b]foo [u]to the[/u] bar[/b]';
var exptags = /\[(b|u|i|s|center|code){1}]((.){1,}?)\[\/(\1){1}]/ig;
while (s.match(exptags)) {
s = s.replace(exptags, "<$1>$2</$1>");
}
document.writeln('<div>' + s + '</div>'); // after
- {1} 当不存在其他计数说明符时,假定为
- {1,}可以缩短为+
var s = '[b]hello[/b] [u]world[/u] [b]foo [u]to the[/u] bar[/b]';
var exptags = /\[(b|u|i|s|center|code){1}]((.){1,}?)\[\/(\1){1}]/ig;
while (s.match(exptags)) {
s = s.replace(exptags, "<$1>$2</$1>");
}
document.writeln('<div>' + s + '</div>'); // after
- {1} 当不存在其他计数说明符时,假定为
- {1,}可以缩短为+
- 同意Richard Szalay的观点,但他的正则表达式没有被正确引用:
var exptags = /\[(b|u|i|s|center|code)](.*)\[\/\1]/ig;
它更干净。请注意,我还将+?
更改为*
。+?
有两个问题:
同意Richard Szalay的观点,但他的正则表达式没有被正确引用:
var exptags = /\[(b|u|i|s|center|code)](.*)\[\/\1]/ig;
它更干净。请注意,我还将+?
更改为*
。+?
有两个问题:
<b><i>helloworld</i></b>
<b>helloworld</b>
var tagreg = /\[(\/?)(b|u|i|s|center|code)]/ig
div.innerHTML="[b][i]helloworld[/b]".replace(tagreg, "<$1$2>") //no closing i
//div.inerHTML=="<b><i>helloworld</i></b>"