加快StreamReader的搜索/读取速度

时间:2014-05-22 06:12:17

标签: c# search streamreader ftpwebrequest

我正在尝试下载FTP服务器中存在的文件名列表,一旦我检索所有名称,我就使用StreamReader对象并尝试搜索所有文件名以检查是否存在任何文件所包含的子字符串出现在那个ftp。

例如,如果文件名是

0000730970-0633788104-20140422073022-0633788104.PDF

0000730970-0633789720-20140422101011-0633789720.PDF

0000730970-0633798535-20140425075011-0633798535.PDF

0000730970-0633798536-20140425075011-0633798536.PDF

0000730970-0633804266-20140428124147-0633804266.PDF

0000730970-0633805880-20140429065011-0633805880.PDF

我将搜索“0633798535”(由破折号分隔的第二个或最后一个子字符串,因为这是我对该ftp中存在的那些文件的唯一信息,不知道完整的文件名)。我正在使用的Bellow代码

try{
browseRequest = (FtpWebRequest)FtpWebRequest.Create(ftpAddress);

browseRequest.Credentials = new NetworkCredential(username, password);
browseRequest.UsePassive = true;
browseRequest.UseBinary = true;
browseRequest.KeepAlive = true;

browseRequest.Method = WebRequestMethods.Ftp.ListDirectory;
response = (FtpWebResponse)browseRequest.GetResponse();
responseStream = response.GetResponseStream();

if (responseStream != null)
{
    using (StreamReader reader = new StreamReader(responseStream))
    {
        while (!reader.EndOfStream && !isDownloaded)
        {
            string fileName = reader.ReadLine().ToString();
            if (fileName.Contains(subStringToBeFind)) //search for the first encounter
            {
                //download the file
                isDownloaded = true; //initially false
            }
        }
    }
}
}

这里我使用顺序搜索来查找文件名。但问题是,如果文件数量很大,搜索速度很慢,比如82000文件名,如果我正在寻找最后一个文件,就像2分钟搜索一样。因此,应用程序很慢。所以,我需要帮助来加速搜索。有没有办法使用二进制搜索或其他东西来改善搜索时间。

1 个答案:

答案 0 :(得分:3)

如果您已经拥有了所有数据,那么您只能使用二进制搜索(如果它已经排序,它可能就在这里)。我强烈怀疑瓶颈不是这里的Contains方法 - 我希望它是数据传输。虽然我会做出三个改变,但看起来它已经看起来相当有效了:

  • 使用ReadLine()在输入结尾处返回null而非使用EndOfStream
  • 的事实
  • 使用声明ReadLine()返回string的事实 - 您无需致电ToString。 (这不会伤害你的表现,但它很难看。)
  • 对响应和响应流使用using语句。您可能没问题,因为您已经为读者提供了using声明,但您至少应该有一个响应本身。

所以:

string line;
while (!isDownloaded && (line = reader.ReadLine()) != null)
{
    if (line.Contains(target))
    {
        isDownloaded = true;
    }
}

要验证它确实是网络是问题而不是Contains调用,请尝试将两者分开(仅用于诊断目的;您不希望在现实,因为你希望能够在找到文件后立即停止:

  • 获取所有文件名,并将它们存储在文件(或内存)中
  • 搜索文件名

时间两个步骤 - 如果你没有发现第一步几乎所有时间,我会感到惊讶。使用Contains搜索82000个字符串应该非常非常快。