Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/283.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 在第三方库代码中中止执行的最安全方法_C#_.net_Thread Abort - Fatal编程技术网

C# 在第三方库代码中中止执行的最安全方法

C# 在第三方库代码中中止执行的最安全方法,c#,.net,thread-abort,C#,.net,Thread Abort,下面是我的解决方案中的一个简化版本的代码,它使用了一个非常容易出错的第三方库代码: public GlitchyThirdPartyComponent GetThirdPartyComponent(Stream stream) { return new GlitchyThirdPartyComponent(stream); } 对于某些流,GlitchyThirdPartyComponent的构造函数完全崩溃,开始消耗大量CPU电源和内存,直到发生OutOfMemoryExceptio

下面是我的解决方案中的一个简化版本的代码,它使用了一个非常容易出错的第三方库代码:

public GlitchyThirdPartyComponent GetThirdPartyComponent(Stream stream)
{
    return new GlitchyThirdPartyComponent(stream);
}
对于某些流,
GlitchyThirdPartyComponent
的构造函数完全崩溃,开始消耗大量CPU电源和内存,直到发生
OutOfMemoryException
时才会退出(闻起来像是某个地方的无限循环)

我试图找出调用
GetThirdPartyComponent
并在某个超时后中止其执行(如果它仍在运行)的最安全的方法

我已经研究了几种可能的解决方案,但似乎没有合适的解决方案。原因有两个:

  • 我无法访问第三方库源代码。所有组件都是模糊的,因此也没有分解
  • GlitchyThirdPartyComponent
    不可序列化,因此没有跨appdomain或跨进程的解决方案
  • GlitchyThirdPartyComponent
    最有可能使用COM(从接口的外观来看),因此
    Thread.Abort
    是一个非常不可靠的选项
  • 虽然可以使用另一个第三方库或向我当前的库供应商咨询错误修复,但这些解决方案需要时间,我的问题应该尽快得到解决

  • 那么,在这种情况下我该怎么办?
    Thread.Abort
    真的是这里最好的解决方案吗?

    您可以将对
    GlitchyThirdPartyComponent
    的调用封装在
    任务中。然后暂停。像这样的

    int timeout = 1000;
    var task = Task.Run(() => new GlitchyThirdPartyComponent(stream))
    if (await Task.WhenAny(task, Task.Delay(timeout)) == task) {
        // task completed within timeout
    } else { 
        // timeout logic
    }
    

    您可以将对GlitchyThirdPartyComponent的调用包装到
    任务中。然后暂停。像这样的

    int timeout = 1000;
    var task = Task.Run(() => new GlitchyThirdPartyComponent(stream))
    if (await Task.WhenAny(task, Task.Delay(timeout)) == task) {
        // task completed within timeout
    } else { 
        // timeout logic
    }
    

    你已经排除了所有显而易见的解决方案,只剩下两个了。使用电话。当没有人拿起时删除库。你使用的是什么版本的.Net?@Padraic我使用的是.Net 4.5.2你已经消除了所有明显的解决方案,只剩下两个了。使用电话。当没有人拿起时删除库。你使用的是什么版本的.Net?@Padraic我使用的是.Net 4.5.2 OP已经知道这是一个选项。问题是在
    //timeout logic
    部分中放置什么。OP已经知道这是一个选项。问题是在
    //超时逻辑
    部分中放置什么。