posts - 7, comments - 29, trackbacks - 0, articles - 0
  博客园 :: 首页 :: 新随笔 :: 联系 :: 订阅 订阅 :: 管理

公告

最新评论

共2页: 1 2 下一页 
貌似SL4不支持Chrome。安装插件的时候说不支持。
private static string BuildInput() { StringBuilder sb = new StringBuilder(); sb.Append(">"); for (int i = 0; i < 100000; i++) { sb.Append("Hello, this is some text ..."); sb.Append("<param" + i + ">"); sb.Append("this is some text..."); } sb.Append("<"); return sb.ToString(); } string t = BuildInput(); string[] tt = Regex.Replace(t, @">.*<", " ",RegexOptions.Compiled).Split(' ');
LastIndexOf,唔,,,,莫非在反向搜索,这的确是正则的硬伤,明天测一下就知道了。
@Ivony... 编译的Regex效率确实会高些,但是你给的代码的结果也是平均一次五百多ms,而且结果其实是不对的。我给的那个Analyzer类,时间复杂度已经是O(n)了,n为输入串长度,平均一次四五十ms,我真的很难相信正则匹配可以达到O(n)的效率...
正则的确应该更高效,但应该使用Regex对象而不是静态方法。 [code=csharp] Regex matchRegex = new Regex( "<(?<result>.*)>", RegexOptions.Compiled ); Regex splitRegex = new Regex( "," , RegexOptions.Compiled) string str="dfsdg<2434>,dgdfg<35346>,dtr35<3w543>"; string[] results = ( from item in spiltRegex.Split( str ) select matchReegx.Match( item ).Groups["result"].Value ).ToArray(); [/code]
顶个
测试应该是公平的,因为在我的Analyzer中我也同样把10W数据加到了List<string>中。 额,不过我的代码也有些问题了,我的_lexemeStart应该放到方法中作为局部变量才对,当然,这对结果影响不大。 我感觉在大字符串情况下用Regex的速度比我上面的代码慢是必然的,因为我的代码只能处理特定领域中的问题(以<开头,>结尾),而正则引擎则可以处理通用的模式匹配问题,因为通用,自然就会损失一定效率,所以我感觉这应该不能算是.net的问题。 PS: 其实就是讨论而已嘛,我本意也不是要分个高下额,只不过我第一条回复把客套话给省了,My bad。:-) 更何况我其实很菜,只是偶尔的一两次幸运点,碰到自个儿弄过的东西,会稍占点上风:)
[quote]Symas2009[/quote] 为这个问题我还专门跑回了单位。修改代码后我测试了一下,在我的机器上结果如下: Regex Time Elapsed: 17,629ms Time Elapsed (one time):352ms CPU time: 17,109,375,000ns CPU time (one time): 342,187,500ns Gen 0: 125 Gen 1: 75 Gen 2: 18 MyAnalyzer Time Elapsed: 3,375ms Time Elapsed (one time):67ms CPU time: 3,281,250,000ns CPU time (one time): 65,625,000ns Gen 0: 41 Gen 1: 21 Gen 2: 7 虽然修改后速度提高了很多,但还是比String慢5倍左右。兄弟我甘拜下风!言语冒犯之处还请多担待!
[quote]Symas2009: 平均时间:47ms 平均时间:1645ms [/quote] 正则可能会比String慢一些,不过要是.net的Regex真实现的这样差,只能说微软的人都是吃闲饭的了。 我无话可说
[quote]Symas2009: PS: 那个正则模式~~[/quote] 这个的确是没考虑周全。不过你把MatchCollection的10万个元素弄到List里,然后再跟我比效率,你觉得合适吗?建议重写。 最后,匿名用户不能粘代码。
PS: 那个正则模式(?<=<)\w+好像还有点小瑕疵: <hello<hello>world<haha> 这种情况我感觉应该只输出hello和haha比较合适额~~
e,顺便请教下,如何在评论中插入高亮的代码呢?Thx:)
class Program { static void Main(string[] args) { Analyzer analyzer = new Analyzer(); string input = BuildInput(); int interation = 50; CodeTimer.Time("Regex", interation, () => { ExtraDataWithRegex(input); }); CodeTimer.Time("MyAnalyzer", interation, () => { analyzer.ExtractData(input); }); Console.WriteLine("Press any key to continue..."); Console.ReadKey(); } // 你的 public static IList<string> ExtraDataWithRegex(string input) { List<string> result = new List<string>(); string pattern = @"(?<=<)\w+"; MatchCollection matches = Regex.Matches(input, pattern); foreach (Match m in matches) { result.Add(m.Value); } return result; } // 构建测试字符串 private static string BuildInput() { StringBuilder sb = new StringBuilder(); for (int i = 0; i < 100000; i++) { sb.Append("Hello, this is some text ..."); sb.Append("<param" + i + ">"); sb.Append("this is some text..."); } return sb.ToString(); } }
// 我的 public class Analyzer { public const char Left = '<'; public const char Right = '>'; private int _lexemeStart = -1; public IList<string> ExtractData(string input) { List<string> result = new List<string>(); for (int i = 0; i < input.Length; i++) { if (input[i] == Left) { _lexemeStart = i; } else if (_lexemeStart >= 0 && input[i] == Right) { result.Add(input.Substring(_lexemeStart + 1, i - 1 - _lexemeStart)); } } return result; } }
好吧,我就不用100W了,要等太久,我用10W数据吧(也就是有10W的<xxx>),我写的类叫Analyzer,你的方案我就直接用静态方法调用了,在我的机子上Release测试的结果是(用elaget的CodeTimer): **我的**: 平均时间:47ms 内存方面: Gen 0: 37 Gen 1: 26 Gen 2: 10 **你的**: 平均时间:1645ms 内存方面: Gen 0: 184 Gen 1: 128 Gen 2: 45 ---------------------------------- 代码如下:
[quote]Symas2009: @楼上 我曾经测试过,用正则做这种提取并不很高效,尤其在字符串大时 其实我觉得高效的作法不应做Split,像你这种简单的匹配情况,一次遍历(所有字符)就可以实现提取出所有的<..>中的值。[/quote] 怎么提取还要用代码说话,效率高不高用这个例子(乘100万后)比比就知道
@楼上 我曾经测试过,用正则做这种提取并不很高效,尤其在字符串大时 其实我觉得高效的作法不应做Split,像你这种简单的匹配情况,一次遍历(所有字符)就可以实现提取出所有的<..>中的值。
Re:字符串数组去掉重复值方法 yanxy 2010-02-27 13:39  
用Python一句话搞定: [code=python] print set(["1", "1", "2", "3", "4", "33", "4", "66", "77", "2", "44", "33"]) [/code]
刚才在家,没法写代码。现在上代码:[code=csharp] string str = "dfsdg<2434>,dgdfg<35346>,dtr35<3w543>"; string pattern = @"(?<=<)\w+"; MatchCollection matches = Regex.Matches(str,pattern); foreach (Match result in matches) Console.WriteLine(result); [/code] 注意要先using System.Text.RegularExpressions; 正则干这种文本处理的事情比较高效,但可读性不好,不如Linq。 另外你的代码1可能是错的,你自己试验一下,在我这里怎么输出: dfsdg<2434> dgdfg<35346> dtr35<3w543> ??
用正则更简单高效
共2页: 1 2 下一页