2009-07-26 84 views
12
WebResponse response; 
try 
{     
HttpWebRequest request = (HttpWebRequest)WebRequest.Create(url); 
request.Timeout = 20000; 
response = request.GetResponse(); 

request = (HttpWebRequest)WebRequest.Create(url2); 
response = request.GetResponse(); 
} 
catch(Exception ex) 
{ 
//do something 
}    
finally 
{ 
} 

应该在哪里调用response.Close()?何时调用WebResponse.Close()

  • 每个GetResponse()在尝试?

  • 最后一次GetResponse()在try - once?

  • 在finally块?

回答

19

以上都不对。你应该使用using块:

HttpWebRequest request = (HttpWebRequest)WebRequest.Create(url); 
request.Timeout = 20000; 
using (WebResponse response = request.GetResponse()) 
{ 
    using (var stream = response.GetResponseStream()) 
    { 
     using (var reader = new StreamReader(stream)) 
     { 
      var result = reader.ReadToEnd(); 
      // Do something with result 
     } 
    } 
} 

一个using块将确保调用Dispose方法,无论是否有异常。 Dispose将执行与Close相同的操作。

using (var d = new DisposableClass()){code;} 

等同于:使用嵌套块不需要花括号,提高可读性

DisposableClass d = null; 
try 
{ 
    d = new DisposableClass(); 
    code; 
} 
finally 
{ 
    if (d != null) 
     ((IDisposable)d).Dispose(); 
} 
1

把它放在finally块中。按MSDN

为 清理在 分配try块的任何资源以及运行任何代码 即使 是一个例外,必须执行finally块是非常有用的。无论 如何尝试块退出,控制始终是 传递到finally块。

+0

但是,如果他将response.Close()放在最后,他会得到'使用未分配的变量'错误。 – UpTheCreek 2011-04-29 21:08:51

-1

我建议以下

 try 
     { 
      HttpWebRequest request = (HttpWebRequest)WebRequest.Create("http://www.google.com"); 
      request.Timeout = 20000; 
      using (var response = request.GetResponse()) 
      { 
       //Do something with response. 
      } 


      request = (HttpWebRequest)WebRequest.Create("http://www.bing.com"); 
      using (var response = request.GetResponse()) 
      { 
       //Do somehing with response 
      } 
     } 
     catch (Exception ex) 
     { 
      //do something 
     } 
     finally 
     { 
     } 
+1

当然,您需要处理/关闭第一个“请求”实例,因为您只需用新的实例覆盖该实例,那么当垃圾收集器处理第一个实例时,您将受到垃圾收集器的摆布。 – Marineio 2009-07-26 13:37:30

+2

WebRequest不实现IDisposable。 – 2009-07-26 13:41:26

+0

这里没有理由为`finally`块。另外,在`catch`中没有一些实际的代码,这个答案可能会让所有代码都需要`try/catch`的错误印象。 – 2015-04-09 19:52:47

0

注意。所以John Saunder的代码可以写成:

HttpWebRequest request = (HttpWebRequest)WebRequest.Create(url); 
request.Timeout = 20000; 
using (WebResponse response = request.GetResponse()) 
using (var stream = response.GetResponseStream()) 
using (var reader = new StreamReader(stream)) 
{ 
    var result = reader.ReadToEnd(); 
    // Do something with result 
} 

VS.NET知道这样的嵌套块不需要缩进。注意顺便说一句,如果你知道响应的编码,或者无论如何都会忽略它,WebClient提供了一个更简单的API--缺少标题信息,所以基于标题的(传输/文本)编码检测变得不可能,但否则它工作正常。