• 【原译】四种方法统计字符串的行数&执行时间比较


    免责申明(必读!):本博客提供的所有教程的翻译原稿均来自于互联网,仅供学习交流之用,切勿进行商业传播。同时,转载时不要移除本申明。如产生任何纠纷,均与本博客所有人、发表该翻译稿之人无任何关系。谢谢合作!

    原文链接地址:http://www.codeproject.com/Tips/312312/Counting-lines-in-a-string

    我需要统计一下字符串的行数,因此我就写了一个超级没有技术含量的蛮力方法来统计了。

    static long LinesCount(string s)
    {
    long count = 0;
    int position = 0;
    while ((position = s.IndexOf('\n', position)) != -1)
    {
    count++;
    position++; // Skip this occurance!
    }
    return count;
    }


    这个函数他呀,运行正常,写起来也快。

    但是,我就像啊,这是不是也太没有技术含量了,难道就没有其他方法了?

    当然有,我想出了两种方法:正则和Linq,我把这些方法都写出来

    static long LinesCountIndexOf(string s)
    {
    long count = 0;
    int position = 0;
    while ((position = s.IndexOf('\n', position)) != -1)
    {
    count++;
    position++; // Skip this occurance!
    }
    return count;
    }
    static Regex r = new Regex("\n", RegexOptions.Multiline);
    static long LinesCountRegex(string s)
    {
    MatchCollection mc = r.Matches(s);
    return mc.Count;
    }
    static long LinesCountLinq(string s)
    {
    return (from ch in s
    where ch== '\n'
    select ch).Count();
    }
    static long LinesCountSplit(string s)
    {
    return (s.Split(new char[] { '\n' })).Length;
    }

    然后呢,我又写了一个快速但混乱的毫无技术含量的测试程序来测试正确性

    string s = File.ReadAllText(@"D:\Temp\MyLargeTextFile.txt");
    long index = LinesCountIndexOf(s);
    long regex = LinesCountRegex(s);
    long linq= LinesCountLinq(s);
    Console.WriteLine("{0}:{1}:{2}", index, regex, linq);
    Stopwatch si = new Stopwatch();
    Stopwatch sd = new Stopwatch();
    Stopwatch sl = new Stopwatch();
    Stopwatch ss = new Stopwatch();
    si.Start();
    for (int i = 0; i < 100; i++)
    {
    index = LinesCountIndexOf(s);
    }
    si.Stop();
    ss.Start();
    for (int i = 0; i < 100; i++)
    {
    index = LinesCountSplit(s);
    }
    ss.Stop();
    sd.Start();
    for (int i = 0; i < 100; i++)
    {
    index = LinesCountRegex(s);
    }
    sd.Stop();
    sl.Start();
    for (int i = 0; i < 100; i++)
    {
    index = LinesCountLinq(s);
    }
    sl.Stop();

    输入的文件是1.64Mb,包含大约23K行。

    测试结果显示是

    22777:22777:22777

    有意思的是这个执行时间的结果(ms计)

    Test    ElapsedMilliseconds
    BF+I 181
    Split 1089
    Regex 2557
    Linq 3590

    我本来想着这正则要快的不是一点点啊。正则和Linq这么大的差异令我震惊了,最令我震惊的是BF+I竟然比他们两个都快,而分割则毫无疑问比Index要慢,因为在分割方法中.net一次要分配23k的字符串空间

    为了完成任务,我把BF+I版本重写了一个类,并且判断了字符串只有一行的情况,如你期望的一样,不要一秒就完成了

    static class ExtensionMethods
    {
    /// <summary>
    /// Returns the number of lines in a string
    /// </summary>
    /// <param name="s"></param>
    /// <returns></returns>
    public static long Lines(this string s)
    {
    long count = 1;
    int position = 0;
    while ((position = s.IndexOf('\n', position)) != -1)
    {
    count++;
    position++; // Skip this occurance!
    }
    return count;
    }
    }

    注:count初始为1后,时间更短了一些。

    Test    ElapsedMilliseconds
    BF+I 170
    Split 1089
    Regex 2063
    Linq 3583

    完成。。
    著作权声明:本文由http://www.cnblogs.com/lazycoding翻译,欢迎转载分享。请尊重作者劳动,转载时保留该声明和作者博客链接,谢谢!


  • 相关阅读:
    Navicat破解安装
    jrebel and xrebel
    JMTER连接数据库
    jmter参数化
    JMTER逻辑控制器
    JMter定时器和聚合报告
    Jmter文件上传
    npm安装教程
    adb调试工具
    Jmter前/后置处理器
  • 原文地址:https://www.cnblogs.com/lazycoding/p/2317552.html
Copyright © 2020-2023  润新知