2012-10-15 56 views
1

好的,我明白这可能是非常愚蠢的问题,但我从来没有做过,所以我问这个问题。我如何使用Thread类下载文件(比方说,来自互联网)?下载文件(使用线程类)

回答

1

你是什么意思“使用线程类”?我想你想下载一个文件进行线程化,所以它不会阻止你的用户界面或程序的其他部分。

我假定你使用C++和WINAPI。 首先创建一个线程。 This tutorial提供有关WIN32线程的良好信息。 此线程将负责下载文件。要做到这一点,您只需连接到端口80上的Web服务器,并发送您想要的文件的HTTP GET请求。这可能与此类似(注意换行符):

GET /path/to/your/file.jpg HTTP/1.1\r\n 
Host: www.host.com\r\n 
Connection: close\r\n 
\r\n 
\r\n 

服务器将然后用含有与前一个头文件HTTP响应回答。解析此标题并阅读内容。

More information on HTTP can be found here.

+0

是的,我想在下载时不阻止我的程序。我是.net初学者,c#,而不是C++。据我所知,win32线程与.net线程不同,请纠正我,如果我错了。所以,从愚蠢的问题开始。为什么我不能让水木清华这样的: 线程的线程=新主题(新的ThreadStart(的someMethod)) 无效的someMethod() – Viaches

+0

AFAIK C#{线程下载 代码}都是围绕WIN32线程包装。 但这没关系,当然你可以使用你在那里写的方法。 ;) 只需在您提供给线程构造函数的函数中编写下载代码即可。然后,此方法中的代码将与您的其他代码同时执行。 对于下载部分,请查看维基百科上的套接字和HTTP协议。 – maxdev

+0

好的,谢谢你的帮助! – Viaches

1

如果会建议你不要使用线程下载文件。最好使用更针对I/O的异步构造,因为它们会比线程产生更低的开销。我不知道你正在使用的.NET Framework的版本,但在4.5,这样的事情应该工作:

private static Task DownloadFileAsync(string uri, string localPath) 
{ 
    // Get the http request 
    HttpWebRequest webRequest = WebRequest.CreateHttp(uri); 

    // Get the http response asynchronously 
    return webRequest.GetResponseAsync() 
     .ContinueWith(task => 
      { 
       // When the GetResponseAsync task is finished, we will come 
       // into this contiuation (which is an anonymous method). 

       // Check if the GetResponseAsync task failed. 
       if (task.IsFaulted) 
       { 
        Console.WriteLine(task.Exception); 
        return null; 
       } 

       // Get the web response. 
       WebResponse response = task.Result; 

       // Open a file stream for the local file. 
       FileStream localStream = File.OpenWrite(localPath); 

       // Copy the contents from the response stream to the 
       // local file stream asynchronously. 
       return response.GetResponseStream().CopyToAsync(localStream) 
        .ContinueWith(streamTask => 
         { 
          // When the CopyToAsync task is finished, we come 
          // to this continuation (which is also an anonymous 
          // method).  
          // Flush and dispose the local file stream. There 
          // is a FlushAsync method that will flush 
          // asychronously, returning yet another task, but 
          // for the sake of brevity I use the synchronous 
          // method here. 
          localStream.Flush(); 
          localStream.Dispose(); 

          // Don't forget to check if the previous task 
          // failed or not. 
          // All Task exceptions must be observed. 
          if (streamTask.IsFaulted) 
          { 
           Console.WriteLine(streamTask.Exception); 
          } 
         }); 
       // since we end up with a task returning a task we should 
       // call Unwrap to return a single task representing the 
       // entire operation 
      }).Unwrap(); 
} 

你会想阐述一下错误处理了一下。简而言之,此代码的作用如下:

请参阅代码注释以获取有关其工作原理的更详细说明。