2014-03-14 92 views
0

我有一个包含多个子目录的目录,每个子目录有多个10K xml文件。从超过10K个文件的目录中读取文件

当有1000个文件时,它用于读取5 secs中的随机文件,而增加文件数量则需要多于12 seconds

我使用下面的代码为retriving文件内容: -

if (File.Exists(xmlLogFilePath)) 
{  
     string retrivedText = File.ReadAllText(xmlLogFilePath);  
} 

有人建议可以什么可以做,以提高性能。

.NET版本:2.0

+0

那么速度在哪里?编写文件或遍历目录或检查文件是否存在 - 或其他地方?你有没有计时,看看时间到了哪里?你在12秒内写了多少个文件? –

+0

@Matthew,阅读文件需要时间 –

+1

那么你不可能加快速度。文件有多大?它一定很大......有没有什么办法可以使它变小 - 也许通过每隔一段时间删除一些旧线(假设它是一个日志文件)?你是否可以每周创建一个新文件,方法是以某种方式在年份和星期编号之后命名文件? –

回答

0

下面是要考虑几个方面:

  1. 移动数据到数据库,考虑到大量的文件。
  2. 如果这不可行,请尝试将硬盘升级到固态硬盘。
  3. 或者,您可以将文件拆分到独立的磁盘上并且并行读取。
+0

时间消耗在阅读文件这不会帮助我相信 –

+0

原来的问题有“WriteAllText()”.. – bit

+0

我道歉应该已经ReadAllText –

2

可以使用并行异步I/O方法:

下面的例子写10个文本文件演示了并行处理。

public async void ProcessWriteMult() 
{ 
    string folder = @"tempfolder\"; 
    List<Task> tasks = new List<Task>(); 
    List<FileStream> sourceStreams = new List<FileStream>(); 

    try 
    { 
     for (int index = 1; index <= 10; index++) 
     { 
      string text = "In file " + index.ToString() + "\r\n"; 

      string fileName = "thefile" + index.ToString("00") + ".txt"; 
      string filePath = folder + fileName; 

      byte[] encodedText = Encoding.Unicode.GetBytes(text); 

      FileStream sourceStream = new FileStream(filePath, 
       FileMode.Append, FileAccess.Write, FileShare.None, 
       bufferSize: 4096, useAsync: true); 

      Task theTask = sourceStream.WriteAsync(encodedText, 0, encodedText.Length); 
      sourceStreams.Add(sourceStream); 

      tasks.Add(theTask); 
     } 

     await Task.WhenAll(tasks); 
    } 

    finally 
    { 
     foreach (FileStream sourceStream in sourceStreams) 
     { 
      sourceStream.Close(); 
     } 
    } 
} 
+2

为什么这个downvote。? –

+0

我想这是因为这里描述的并行处理属于.NET 4.0。这个问题涉及.NET 2.0。无论如何,这不值得downvote恕我直言。 – Larry

+2

考虑到速度限制因素很可能是IO,并行化并不会有很大帮助。事实上,由于任务调度的开销,情况可能会更糟糕。这适用于写作和阅读。 –

1

减速是由两个不同的因素造成的。

首先,因为有更多的文件,它们将占用更多的空间。当你想读取一个“随机”文件时,它在磁盘缓存中的概率将会降低。这会增加读取文件的平均时间,并且除了增加计算机中RAM的数量外,您可以做的更多。

其次,目录是需要搜索文件的数据结构。随着目录增加,即随着目录中文件的数量增加,这将花费更长的时间。这你可以使用:确保你的目录更小。例如,为文件名以给定字符开头的所有文件创建一个目录。这将加快搜索速度。

0

我觉得你在搜索文件系统中的文件记录时失去了时间。在上面的例子中,你做了两次:第一次使用Exists()调用,第二次使用ReadAllText()打开文件。可能,您可以使用FileInfo结构最大限度地减少文件目录访问。但我宁愿重新组织文件,以便一个目录包含不超过1000个文件。

0

根据File.ReadAllText(String path)的实现,它使用默认缓冲区大小为1024字节的StreamReader(至少在.NET 4.5.1中 - 我不确定它是否已更改)。但是,您可以通过使用更高的缓冲区大小来提高读取文件的性能,从而减少后台的调用次数。