求教:正则表达式的效率问题

Cipherf 2007-06-11 06:48:08
//去除<style></style>之间的内容
Regex re = new Regex(@"<style[\s\S]*?</style\s*?>", RegexOptions.IgnoreCase | RegexOptions.Compiled);
text = re.Replace(text.ToString(), "");
//去除<!-- -->之间的内容
re = new Regex(@"<!--[\s\S]*?-->", RegexOptions.IgnoreCase | RegexOptions.Compiled);
text = re.Replace(text.ToString(), "");
//去除<script></script>之间的内容
re = new Regex(@"<script[\s\S]*?</script\s*?>", RegexOptions.IgnoreCase | RegexOptions.Compiled);
text = re.Replace(text.ToString(), "");

问题主要是3个
1.因为不知道怎么对re重新赋值,就用= new Regex的方法,这样好吗?之前的那个regex的资源会自动回收的是么?

2.为了提高效率,<style[\s\S]*?</style\s*?>中间的懒惰限定*?去掉后会不会有漏洞
改成<style[\s\S]*</style\s*>还是怎么改?其他的两个式子也请帮忙看看

3.效率的问题,样本是个17k左右的网页文件,上面的耗时0.0136576
但是把RegexOptions.Compiled去掉后,耗时0.0002411
不是说Compiled可以提升运行速度的么,怎么反而是去掉后快啊?Compiled有什么意义?要怎么再提升效率?

谢谢大家了
...全文
309 7 打赏 收藏 转发到动态 举报
写回复
用AI写文章
7 条回复
切换为时间正序
请发表友善的回复…
发表回复
yuanzhihua520 2007-06-12
  • 打赏
  • 举报
回复
up
-过客- 2007-06-12
  • 打赏
  • 举报
回复
楼上测得真细,我正则都是在给别人解决问题的过程中学习的,自己应用基本上还没遇到过,更不要说涉及到效率的问题了,所以也就没有花费多少时间和精力去研究

其实感觉正则涉及到效率的地方不是很多,一般以下几种情况综合在一起时才需要考虑
1、源数源比较大
2、运用了较复杂的正则表达式
3、大量运用正则表达式
4、多次运用同一正则表达式

一般在使用较复杂的正则表达式时,正则书写对效率影响比较大,我以前遇到过一次,就是在一个表达式中,非贪婪模式用得太多,导致效率过低,处理一个文本要3秒多钟,后来去掉了一些无用的非贪婪模式,提高到0.2秒以内,又换了种方式,用委托来做,提高到0.01秒内

有关正则效率问题,可以看下这篇文章
http://www.regexlab.com/zh/regtopic.htm
Cipherf 2007-06-12
  • 打赏
  • 举报
回复
感谢lxcnn的指点,把style和script组合在一起真是巧妙。子表达式反向引用虽然看过了,但是没想到自己也能用...经验不足
Regex的静态方法也很好用,方便。

关于compiled,上面那段MSDN里面也说到编译的资源问题。按楼上的方法测试了一下,略有一点改动,把replace改成了match,因为发现第一次替换后,以后的99次自然找不到匹配了,可能会影响正确性。结果是
compiled:
00:00:00.0109246
0.0109661
0.0113060
非编译
0.0032480
0.0027570
0.0027517

编译还是完败。

顺便的测试是,
1.Regex静态方法从速度上来说,比创建一个实例快那么一点点,但几乎可忽略不计
2.组合的反向引用居然略慢于分开的3个式子,汗,因此我就keep it simple, stupid了
3.最后测试是拿手里现有的最大html试了一下,同样是100次,样本为白饭如霜的疯狂植物园带回帖版1329k,结果是:
编译:
0.0160975
0.0144234
0.0146817
解释:
0.0094024
0.0088975
0.0090097
我不管了,就算编译有什么潜在的好处,也不用了。好在即使在比我慢10倍的古董机器上,执行时间也不过是几个毫秒的级别差别。
runrunrun 2007-06-11
  • 打赏
  • 举报
回复
compile 应该是在多次运行时才会增加效率吧
比如用下面这句话测试一下:
for( int i=0; i<100; i++ ) text = re.Replace(text.ToString(), "");
greenery 2007-06-11
  • 打赏
  • 举报
回复
up
hxshanji 2007-06-11
  • 打赏
  • 举报
回复
又见正则之神,mark
-过客- 2007-06-11
  • 打赏
  • 举报
回复
效率方法研究的比较少,这样试下吧

yourStr = Regex.Replace(yourStr, @"<(style|script)[^>]*>[\s\S]*?</\1>", "", RegexOptions.IgnoreCase);
yourStr = Regex.Replace(yourStr, @"<!--[^>]*-->", "");

比如说<style[\s\S]*?</style\s*?>,如果去掉“?”要保证你的源字符串中只有一对<style>标签,否则第一个<style>和最后一个</style>标签之间的内容都会被替换掉

Compiled 指定正则表达式将被编译为程序集。生成该正则表达式的 Microsoft 中间语言 (MSIL) 代码;以较长的启动时间为代价,得到更快的执行速度。

当然,Compiled对效率的影响并不只是表现在这上面,参考MSDN,这里有对Compiled参数使用更加详细的说明
ms-help://MS.MSDNQTR.v80.chs/MS.MSDN.v80/MS.VisualStudio.v80.chs/dv_fxfund/html/182ec76d-5a01-4d73-996c-0b0d14fcea18.htm

110,539

社区成员

发帖
与我相关
我的任务
社区描述
.NET技术 C#
社区管理员
  • C#
  • Web++
  • by_封爱
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

让您成为最强悍的C#开发者

试试用AI创作助手写篇文章吧