逐行读取文件的最快方法?

时间:2016-01-28 01:36:51

标签: c# arrays

我目前有一个.TXT文件,我试图读取所有行,然后对它们进行排序,然后按顺序显示它们。

这就是我所拥有的

                string inFile = "Z:/Daniel/Accounts.txt";
                string outFile = "Z:/Daniel/SortedAccounts.txt";
                var contents = File.ReadAllLines(inFile);
                Array.Sort(contents);
                File.WriteAllLines(outFile, contents);

                int i = 0;
                int lineCount = File.ReadLines("Z:/Daniel/SortedAccounts.txt").Count();
                do
                {
                    string accounts = File.ReadLines("Z:/Daniel/SortedAccounts.txt").Skip(i).Take(1).First();
                    //First Name
                    int pFrom1 = accounts.IndexOf("#1#") + "#1#".Length;
                    int pTo1 = accounts.LastIndexOf("#2#");
                    String accountFirstName = accounts.Substring(pFrom1, pTo1 - pFrom1);
                    //Last Name
                    int pFrom2 = accounts.IndexOf("#2#") + "#2#".Length;
                    int pTo2 = accounts.LastIndexOf("#3#");
                    String accountLastName = accounts.Substring(pFrom2, pTo2 - pFrom2);
                    //Email
                    int pFrom3 = accounts.IndexOf("#3#") + "#3#".Length;
                    int pTo3 = accounts.LastIndexOf("#4#");
                    String accountEmail = accounts.Substring(pFrom3, pTo3 - pFrom3);
                    //Phone Number
                    int pFrom4 = accounts.IndexOf("#4#") + "#4#".Length;
                    int pTo4 = accounts.LastIndexOf("#5#");
                    String accountNumber = accounts.Substring(pFrom4, pTo4 - pFrom4);
                    //Preferred Contact
                    int pFrom5 = accounts.IndexOf("#5#") + "#5#".Length;
                    int pTo5 = accounts.LastIndexOf("#6#");
                    String accountPreferredContact = accounts.Substring(pFrom5, pTo5 - pFrom5);
                    //Populate Combobox
                    accountComboBox.Items.Add(accountLastName + "," + accountFirstName);
                    i = i + 1;
                } while (i < lineCount);

Accounts.txt内的内容是

的示例
  

#1#Daniel#2#Mos#3#dasdnmasdda@gmail.com#4#31012304#5#EMAIL#6#   #1#Daniael#2#Mosa#3#dddasdsa@gmail.com#4#310512304#5#EMAIL#6#   #1#Dansdael#2#Mossdsa#3#dasdsdssa@gmail.com#4#31121234#5#TEXT#6#   #1#Danasdl#2#Mosasaa#3#daasda@gmail.com#4#310123304#5#EMAIL#6#   #1#Dandasel#2#Moasddand#3#daasdsda@gmail.com#4#3123551234#5#TEXT#6#   #1#Danasdl#2#Mossdsadd#3#daasddsa@gmail.com#4#310213304#5#TEXT#6#

问题在于,Accounts.txt有时会超过10,000行,然后程序加载需要一段时间。

我编写的代码是否有更快的实现?

2 个答案:

答案 0 :(得分:0)

我的建议:

  1. 逐行读取文件,如file.readlines,流式传输而不是读取整个文件(特别是不按原样读取文件的两倍!)
  2. 对于每一行,应用一个编译的正则表达式,从该字符串中获取所需的值
  3. 创建一个帐户类(或者我猜的只是一个字符串值),根据需要保存2中的所有值。看起来你的循环只关心其中的两个字符串(accountLastNameaccountFirstName
  4. 将这些添加到不是组合框项目的列表中。
  5. 使用linq / sort进行排序,如果你需要对它们进行排序(尽可能少地排序),像items.OrderBy( x => x.LastName ).ThenBy( y => y.FirstName)或其他什么
  6. 在最后将整个项目块添加到组合框中,而不是一次添加一个。理想情况下类似于combobox.Items.AddRange(items)(许多组合框/ etc集合可能会在每次添加一个项目时触发集合更改事件,如果您添加1000个项目可能会产生大量开销)

答案 1 :(得分:0)

所有代码都应以下面的方式重构。您需要测量两种方法的性能。

class Account
    {
        public string FirstName { get; set; }

        public string LastName { get; set; }

        public string Email { get; set; }

        public string Number { get; set; }

        public string PreferredContact { get; set; }

    }
            accountComboBox.Items.AddRange(
                lines.Select(line => Regex.Split(line, "[#\\d#]")).Select(data => new Account
                {
                    FirstName = data[0],
                    LastName = data[1],
                    Email = data[2],
                    Number = data[3],
                    PreferredContact = data[4]
                }).Select(item => string.Format("{0},{1}", item.LastName, item.FirstName)).ToArray()
                );

修改“使用AddRange”

ts