2010-09-26 57 views
6

嗨,我有一個函數,通過網址獲取參數到一個Web服務器上的PHP文件,並等待文件的響應(通常需要10-20秒)。我想把它放在一個循環中,因爲我必須一次將這些Get請求發送給大約5個不同的php文件,但是當我嘗試將它添加到循環中時,函數會使循環等待,直到文件返回響應到下一個。使用C#異步WebRequests使用C#

public string HttpGet(string URI, string Parameters) 
    { 
     HttpWebRequest request = (HttpWebRequest)WebRequest.Create(URI + Parameters); 

     HttpWebResponse response = (HttpWebResponse)request.GetResponse(); 
     StreamReader resStream = new StreamReader(response.GetResponseStream()); 
      return resStream.ReadToEnd().Trim(); 
    } 

    private void SendCommand() 
    { 
     for(int i = 0; i <= 4; i++) 
     { 
      AddRTB(HttpGet(url, paramater)); 
     } 
    } 

有沒有一種方法可以一次發送全部5個請求,而無需等待前一個完成? (我正在考慮線程化,但唉,我從未碰過它,之前我不知道從哪裏開始)

+1

穿線的方式去爲此,雖然你需要等待所有5回覆,然後再繼續。 – ChrisF 2010-09-26 18:38:27

回答

9

而不是使用GetResponse()方法,你可以使用非阻塞呼叫BeginGetResponse()。它需要一個回調,它可以在最終返回時處理對象WebResponse。鏈接中的示例將爲您提供有關如何讓主線程等待所有響應返回的好主意。

9

以下是兩種使用TPL的方法。

所有請求完成您訪問任何結果

var runningTasks = new List<Task<string>>(); 

for (int ii = 0; ii <= 4; ii++) 
{ 
    var wreq = (HttpWebRequest)WebRequest.Create("..." + ii); 

    var taskResp = Task.Factory.FromAsync<WebResponse>(wreq.BeginGetResponse, 
                wreq.EndGetResponse, 
                null); 
    var taskResult = taskResp.ContinueWith(tsk => new StreamReader(tsk.Result.GetResponseStream()).ReadToEnd().Trim()); 
    runningTasks.Add(taskResult); 
} 

Task.WaitAll(runningTasks.ToArray()); 
IEnumerable<string> results = runningTasks.Select(tsk => tsk.Result); 

之前和第二做一些事情,每個結果,因爲它涉及在第一等待:

for (int ii = 0; ii <= 4; ii++) 
{ 
    var wreq = (HttpWebRequest)WebRequest.Create("..." + ii); 

    var taskResp = Task.Factory.FromAsync<WebResponse>(wreq.BeginGetResponse, 
                wreq.EndGetResponse, 
                null); 
    taskResp.ContinueWith(tsk => new StreamReader(tsk.Result.GetResponseStream()).ReadToEnd().Trim()) 
      .ContinueWith((Task<string> trs) => 
       { 
        var result = trs.Result; 
        DoSomthingWithTheResult(result); 
       }); 
} 
+0

+1。即使@ linuxuser27答案沒有錯,這個答案會更好地回答這個問題,並且會更容易實現。 – 2010-09-26 21:42:31

+0

+1事實上,ContinueWith()方法是一個好主意 – linuxuser27 2010-09-26 21:45:38

+0

如果我需要用BeginGetRequestStream/EndGetRequestSteam發送HTTP POST請求的數據,這將如何改變?http://stackoverflow.com/questions/4190903 – 2010-11-16 12:01:57