c# - AppDomain.Unload() 如何中止线程?

标签 c# .net appdomain

根据多种资源(例如,通过 C# 的 MSDN 和 CLR),当我们调用 AppDomain.Unload(userDomain) 时,userDomain 中的线程将被强制抛出 ThreadAbortException,直到我们调用 Thread.ResetAbort 才能停止.所以我尝试了下面的代码来证明我的理解。在默认域中创建的一个线程运行以下代码来调用在另一个域(即用户域)中创建的 FooType 的 foo 对象

    void ThreadRun(object o)
    {       
           try 
           {
                // this call will cross the App domain;
                foo.Run();
            }
            catch (AppDomainUnloadedException EXP)
            {                    
                 Console.WriteLine("Get appdomain unload exception");
            }
            catch (ThreadAbortException EXP)
            {                    
                Console.WriteLine("Get threadAbortException in ThreadRun");
            }
            Console.WriteLine("Strange, this thread is still alive");
     }

下面列出了 Foo.Run 代码(除了 sleep 什么都不做)

public class FooType : MarshalByRefObject {
  public void Run()
  {
    try
    {
        Console.WriteLine("Foo.Run is running at " + Thread.GetDomain().FriendlyName);
        Thread.Sleep(TimeSpan.FromSeconds(1500));
    }
    catch (ThreadAbortException)
    {
        Console.WriteLine("get thread abort exception");
    }
  }
}

如果我尝试卸载 userDomain,令我惊讶的是 ThreadAbortException 仅在 FooType:Run()(在 userDomain 中)中被捕获,而不是在 ThreadRun() 方法(在 defaultDomain 中)中被捕获。而ThreadRun()只会得到AppDomainUnlo adException然后继续运行。

如果我尝试在不卸载域的情况下直接中止线程,则会在这两个地方出现 ThreadAbortException。

我想知道这种差异是否应该发生?非常感谢

最佳答案

当您卸载 userDomain 时,当前在该域中工作的线程将获得 AbortException。但是,同一个线程也“在”另一个 AppDomain(主线程)中。将 AppDomain 作为数据分隔符而不是执行分隔符,CLR 无法中止生成多个 AppDomain 的线程。这就是为什么你只会得到 UnloadedException。

当您调用 Thread.Abort 时 - 您正在显式中止线程的执行,而不管它当前进入的 AppDomain。

无论如何,当您只想卸载一些 AppDomain 时,您不希望您的线程被中止。

关于c# - AppDomain.Unload() 如何中止线程?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6451705/

相关文章:

c# - 适当使用 BlockingCollection

c# - 使用 CultureAndRegionInfoBuilder 更新内置的 .Net 文化

c# - 处理来自子 AppDomain 的不可序列化的未处理异常

c# - 为什么我调用 ASPNET Core 2.1 Database Migrate 的实现实际上没有应用迁移?

c# - Visual Studio 2015 封装字段

c# - WPF ComboBox 中带有列的不可选择的标题

.net - 如何先用 Entity Framework 数据库获取数据库信息?

.net - 卸载 AppDomains

apache - Java 重定向 + 域

c# - Control.Invoke 展开外部异常并传播内部异常