2015-02-05 63 views
2

我遇到了一个问题,其中ObjectDisposedException大约有50%的时间被抛出。下面的try(在finally之内)中的代码引起了异常。我不知道如何处理这个。我可以吃掉异常,如下所示,但有没有办法检查和关闭对象而不会发生异常?正确避免ObjectDisposedException

public static FindResponse Discover(FindCriteria findCriteria, 
             DiscoveryEndpoint discoveryEndpoint = null) 
    { 
     DiscoveryClient discoveryClient = null; 

     try 
     { 
      if (discoveryEndpoint == null) { 
       discoveryEndpoint = new UdpDiscoveryEndpoint(); 
      } 

      discoveryClient = new DiscoveryClient(discoveryEndpoint); 

      return discoveryClient.Find(findCriteria); 
     } 
     finally 
     { 
      try 
      { 
       if (discoveryClient != null) 
       { 
        discoveryClient.Close(); 
       } 
      } 
      catch (ObjectDisposedException) 
      { 
       // Eat it. 
      } 
     } 
    } 
+0

你可以请张贴堆栈跟踪? –

回答

2

如何

public static FindResponse Discover(FindCriteria findCriteria, DiscoveryEndpoint discoveryEndpoint = null) 
{ 
    if (discoveryEndpoint == null) 
     discoveryEndpoint = new UdpDiscoveryEndpoint(); 

    using (var client = new DiscoveryClient(discoveryEndpoint)) 
    { 
     return client.Find(findCriteria); 
    } 
} 

更新

似乎DiscoveryClient.Dispose()会抛出异常。 OP的原创方法似乎是唯一可以接受的答案。

+0

我应该想到这一点。 :) 谢谢。 –

+0

Ahhhhhh !!我再次遇到异常!我可能只需要抓住它并吃掉它。 –

+0

哦,我已经看到与WCF客户端相同的问题(关闭和处置)。最好只是按照你最初的建议吃。见http://stackoverflow.com/questions/23867/closing-and-disposing-a-wcf-service –

-1

另外我会建议使用“使用”的IDisposable对象。考虑DiscoveryClient是IDisposable接口,

public static FindResponse Discover(FindCriteria findCriteria, DiscoveryEndpoint discoveryEndpoint = null) 
    { 

     FindResponse response = null; 
     try 
     { 
      if (discoveryEndpoint == null) { discoveryEndpoint = new UdpDiscoveryEndpoint(); } 

      using (DiscoveryClient discoveryClient = new DiscoveryClient(discoveryEndpoint)) 
      { 
       response = discoveryClient.Find(findCriteria); 
       discoveryClient.Close(); 
      } 
     } 
     finally 
     { 
      // other finalizing works, like clearing lists, dictionaries etc. 
     } 
     return response; 
    } 
+0

对不起,但'finally {}'是一个没有操作。 –

+0

@RichardSchneider,我想,我已经编好了正确的代码。 。 ..。 –

1

虽然我不明白为什么你碰到它,但你可以试试下面的正常WCF客户端:

如果你有“国家”的属性可以用discoveryClient然后,请尝试以下防御性检查:

finally 
     { 
      try 
      { 
       if (discoveryClient != null) 
       { 
        if(discoveryClient.State == CommunicationState.Faulted) 
        { 
        discoveryClient.Abort(); 
        } 
        else if(discoveryClient.State != CommunicationState.Closed) 
        { 
        discoveryClient.Close(); 
        } 
      } 
      catch (ObjectDisposedException) 
      { 

      } 
     } 

希望这对你有所帮助。

+0

你的'if'检查和'if'里面的内容不能改变吗? –

+0

@BobHorn你是对的。但是,从[MSDN](https://msdn.microsoft.com/en-us/library/system.servicemodel.communicationstate.aspx),“Closing”状态是暂时的,相反,最好对non-瞬态“关闭”并相应地更新了我的答案。此外,“Faulted”状态是我们应该仅以Abort关闭频道的另一个状态。 +正如你刚才提到的,如果所有这些状态由于某种原因而滑落,那么最好吞下它:) –

+0

谢谢。在你的例子中,我们仍然需要捕获并且吃掉异常,但是至少代码是明确的。 +1的提示,但我只是想抓住并吃掉异常,而不用担心其他国家。有时你会厌倦编写这样的代码。 :) –

相关问题