如何在多行上使用 JavaScriptregex?

var ss= "<pre>aaaa\nbbb\nccc</pre>ddd";
var arr= ss.match( /<pre.*?<\/pre>/gm );
alert(arr);     // null

我希望 PRE 块被拾起,即使它跨越了换行字符。我还以为“ m”旗就够了。没有。

发帖前找到了答案 给你。由于我认为自己了解 JavaScript (阅读三本书,工作时间长) ,而且 SO 没有现成的解决方案,所以我还是敢于发表文章。在这里扔石头

所以解决办法是:

var ss= "<pre>aaaa\nbbb\nccc</pre>ddd";
var arr= ss.match( /<pre[\s\S]*?<\/pre>/gm );
alert(arr);     // <pre>...</pre> :)

有没有不那么神秘的方法?

编辑: 这个是一个复制品,但因为它比我的更难找到,我不删除。

它提出 [^]作为一个“多行点”。我仍然不明白的是为什么 [.\n]不工作。我猜这就是 JavaScript 的悲哀之一。.

217358 次浏览

[.\n]不能工作,因为[]中的dot(通过正则表达式定义;不仅仅是javascript)表示点字符。你可以使用(.|\n)(或(.|[\n\r]))代替。

[.\n]不起作用,因为.[]中没有特殊含义,它只是一个字面的.(.|\n)是一种指定“任何字符,包括换行符”的方法。如果你想匹配所有换行符,你还需要添加\r来包含Windows和经典Mac OS风格的行结束符:(.|[\r\n])

结果证明这有点麻烦,而且很慢(参见KrisWebDev对细节的回答),所以更好的方法是用[\s\S]匹配所有空白字符和所有非空白字符,它将匹配所有内容,并且更快更简单。

一般来说,不应该尝试使用regexp来匹配实际的HTML标记。例如,请参阅这些 问题以了解更多有关原因的信息。

相反,尝试在DOM中搜索你需要的标记(使用jQuery会让这更容易,但你总是可以使用标准DOM执行document.getElementsByTagName("pre")),然后如果你需要匹配这些内容,则使用regexp搜索这些结果的文本内容。

不要用(.|[\r\n])代替.进行多行匹配。

是否使用[\s\S]代替.进行多行匹配

此外,在不需要的地方使用*?+?量词来避免贪婪,而不是*+。这可能会对性能产生巨大影响。

请参阅我所做的基准测试:https://jsben.ch/R4Hxu

Using [^]: fastest
Using [\s\S]: 0.83% slower
Using (.|\r|\n): 96% slower
Using (.|[\r\n]): 96% slower

注意:你也可以使用[^],但在下面的评论中已弃用。

我已经测试了它(Chrome),它为我工作([^][^\0]),通过改变点(.)与[^\0][^],因为点不匹配换行符(见这里:http://www.regular-expressions.info/dot.html)

var ss= "<pre>aaaa\nbbb\nccc</pre>ddd";
var arr= ss.match( /<pre[^\0]*?<\/pre>/gm );
alert(arr);     //Working

除了上述例子之外,它是另一种选择。

^[\\w\\s]*$

哪里\w是单词,\s是空白

你没有指定你的环境和Javascript (ECMAscript)版本,我知道这篇文章是2009年的,但为了完整,随着ECMA2018的发布,我们现在可以使用s标志来使.匹配'\n',参见https://stackoverflow.com/a/36006948/141801

因此:

let s = 'I am a string\nover several\nlines.';
console.log('String: "' + s + '".');


let r = /string.*several.*lines/s; // Note 's' modifier
console.log('Match? ' + r.test(s); // 'test' returns true

这是最近添加的,在目前的许多环境中都不能工作,例如Node v8.7.0似乎不能识别它,但它可以在Chromium中工作,我正在编写的Typescript测试中使用它,估计随着时间的推移,它会变得更加主流。

[\\w\\s]*

这个问题对我来说非常有帮助,特别是在匹配包含新行在内的多个内容时,每个其他答案最终都只是将所有匹配项分组在一起。

现在有了s(单行)修饰符,它可以让点匹配新行:) \s也会匹配新的行:D

只要在斜杠后面加上s

 /<pre>.*?<\/pre>/gms