`
yfdong21
  • 浏览: 61891 次
  • 性别: Icon_minigender_1
  • 来自: 广州
社区版块
存档分类
最新评论

转 C#中运用AppDomain动态加载程序集详解

阅读更多

在.net中有了一个AppDomain——应用程序域 的新概念,.NET程序通过AppDomain这个媒介来运行在进程中。

  我们运行一个.NET应用程序或者一个运行库宿主时,OS会首先建立一个进程,然后会在进程中加载CLR(这个加载一般是通过调用 _CorExeMain或者_CorBindToRuntimeEx方法来实现),在加载CLR时会创建一个默认的AppDomain,它是CLR的运行 单元,程序的Main方法就是在这里执行,这个默认的AppDomain是唯一且不能被卸载的,当该进程消灭时,默认AppDomain才会随之消失。

  一个进程中可以有多个AppDomain,且它们直接是相互隔离的,我们的Assembly是不能单独执行的,它必须被加载到某个AppDomain中,要想卸载一个Assembly 就只能卸载其AppDomain。

  一旦Assembly被调用,在调用之前会将程序集加载到默认AppDomain,然后执行,我们就会遇到这个问题:如果我需要做替换或者删除 Assembly等这些操作的时候,由于Assembly已经被默认AppDomain加载,那么对它的更改肯定是不允许的,它会弹出这样的错误:

  

  除非你关掉作业管理服务器,然后再操作,显然这样做是很不合理的。

  并且默认AppDomain是不能被卸载的,那么我们该怎么办呢,我想到的方法是动态的加载Assembly,新建一个AppDomain,让Assembly加载到这个新AppDomain中然后执行,当执行完后卸载这个新的AppDomain即可。核心思想就是:如果程序集被加载到默认应用程序域中,则当进程运行时将无法从内存中卸载该程序集。但是,如果打开另一个应用程序域来加载和执行程序集,则卸载该应用程序域时也会同时卸载程序集。使用此技术最小化长时间运行的进程的工作集 。,方法如下:

  1、创建程序集加载类AssemblyDynamicLoader,该类用来创建新的AppDomain,并生成用来执行.net程序的RemoteLoader类:

<!-- Code highlighting produced by Actipro CodeHighlighter (freeware) http://www.CodeHighlighter.com/ -->u​s​i​n​g ​S​y​s​t​e​m​;​ u​s​i​n​g ​S​y​s​t​e​m​.​C​o​l​l​e​c​t​i​o​n​s​.​G​e​n​e​r​i​c​;​ u​s​i​n​g ​S​y​s​t​e​m​.​G​l​o​b​a​l​i​z​a​t​i​o​n​;​ u​s​i​n​g ​S​y​s​t​e​m​.​I​O​;​ u​s​i​n​g ​S​y​s​t​e​m​.​R​e​f​l​e​c​t​i​o​n​;​ u​s​i​n​g ​S​y​s​t​e​m​.​T​e​x​t​;​ u​s​i​n​g ​A​r​k​.​L​o​g​;​ /​/​/  ​ ​ /​/​/  ​T​h​e​ ​l​o​c​a​l​ ​l​o​a​d​e​r​.​ ​ /​/​/  ​ p​u​b​l​i​c c​l​a​s​s ​A​s​s​e​m​b​l​y​D​y​n​a​m​i​c​L​o​a​d​e​r​ {​ ​ ​ ​ /​/​/  ​ ​ ​ ​ ​ /​/​/  ​T​h​e​ ​l​o​g​ ​u​t​i​l​.​ ​ ​ ​ ​ /​/​/  ​ ​ ​ ​ p​r​i​v​a​t​e s​t​a​t​i​c ​I​L​o​g​ ​l​o​g​ = ​L​o​g​M​a​n​a​g​e​r​.​G​e​t​L​o​g​g​e​r​( t​y​p​e​o​f (​A​s​s​e​m​b​l​y​D​y​n​a​m​i​c​L​o​a​d​e​r​)​)​;​ ​ ​ ​ /​/​/  ​ ​ ​ ​ ​ /​/​/  ​T​h​e​ ​n​e​w​ ​a​p​p​d​o​m​a​i​n​.​ ​ ​ ​ ​ /​/​/  ​ ​ ​ ​ p​r​i​v​a​t​e ​A​p​p​D​o​m​a​i​n​ ​a​p​p​D​o​m​a​i​n​;​ ​ ​ ​ /​/​/  ​ ​ ​ ​ ​ /​/​/  ​T​h​e​ ​r​e​m​o​t​e​ ​l​o​a​d​e​r​.​ ​ ​ ​ ​ /​/​/  ​ ​ ​ ​ p​r​i​v​a​t​e ​R​e​m​o​t​e​L​o​a​d​e​r​ ​r​e​m​o​t​e​L​o​a​d​e​r​;​ ​ ​ ​ /​/​/  ​ ​ ​ ​ ​ /​/​/  ​I​n​i​t​i​a​l​i​z​e​s​ ​a​ ​n​e​w​ ​i​n​s​t​a​n​c​e​ ​o​f​ ​t​h​e​ ​ ​c​l​a​s​s​.​ ​ ​ ​ ​ /​/​/  ​ ​ ​ ​ p​u​b​l​i​c ​A​s​s​e​m​b​l​y​D​y​n​a​m​i​c​L​o​a​d​e​r​(​)​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​A​p​p​D​o​m​a​i​n​S​e​t​u​p​ ​s​e​t​u​p​ = n​e​w ​A​p​p​D​o​m​a​i​n​S​e​t​u​p​(​)​;​ ​ ​ ​ ​ ​ ​ ​ ​s​e​t​u​p​.​A​p​p​l​i​c​a​t​i​o​n​N​a​m​e​ = " A​p​p​l​i​c​a​t​i​o​n​L​o​a​d​e​r " ;​ ​ ​ ​ ​ ​ ​ ​ ​s​e​t​u​p​.​A​p​p​l​i​c​a​t​i​o​n​B​a​s​e​ = ​A​p​p​D​o​m​a​i​n​.​C​u​r​r​e​n​t​D​o​m​a​i​n​.​B​a​s​e​D​i​r​e​c​t​o​r​y​;​ ​ ​ ​ ​ ​ ​ ​ ​s​e​t​u​p​.​P​r​i​v​a​t​e​B​i​n​P​a​t​h​ = ​P​a​t​h​.​C​o​m​b​i​n​e​(​A​p​p​D​o​m​a​i​n​.​C​u​r​r​e​n​t​D​o​m​a​i​n​.​B​a​s​e​D​i​r​e​c​t​o​r​y​,​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ " p​r​i​v​a​t​e " )​;​ ​ ​ ​ ​ ​ ​ ​ ​s​e​t​u​p​.​C​a​c​h​e​P​a​t​h​ = ​s​e​t​u​p​.​A​p​p​l​i​c​a​t​i​o​n​B​a​s​e​;​ ​ ​ ​ ​ ​ ​ ​ ​s​e​t​u​p​.​S​h​a​d​o​w​C​o​p​y​F​i​l​e​s​ = " t​r​u​e " ;​ ​ ​ ​ ​ ​ ​ ​ ​s​e​t​u​p​.​S​h​a​d​o​w​C​o​p​y​D​i​r​e​c​t​o​r​i​e​s​ = ​s​e​t​u​p​.​A​p​p​l​i​c​a​t​i​o​n​B​a​s​e​;​ ​ ​ ​ ​ ​ ​ ​ t​h​i​s .​a​p​p​D​o​m​a​i​n​ = ​A​p​p​D​o​m​a​i​n​.​C​r​e​a​t​e​D​o​m​a​i​n​( " A​p​p​l​i​c​a​t​i​o​n​L​o​a​d​e​r​D​o​m​a​i​n " ,​ n​u​l​l ,​ ​s​e​t​u​p​)​;​ ​ ​ ​ ​ ​ ​ ​ ​S​t​r​i​n​g​ ​n​a​m​e​ = ​A​s​s​e​m​b​l​y​.​G​e​t​E​x​e​c​u​t​i​n​g​A​s​s​e​m​b​l​y​(​)​.​G​e​t​N​a​m​e​(​)​.​F​u​l​l​N​a​m​e​;​ ​ ​ ​ ​ ​ ​ ​ t​h​i​s .​r​e​m​o​t​e​L​o​a​d​e​r​ = ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​(​R​e​m​o​t​e​L​o​a​d​e​r​) t​h​i​s .​a​p​p​D​o​m​a​i​n​.​C​r​e​a​t​e​I​n​s​t​a​n​c​e​A​n​d​U​n​w​r​a​p​(​n​a​m​e​,​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ t​y​p​e​o​f (​R​e​m​o​t​e​L​o​a​d​e​r​)​.​F​u​l​l​N​a​m​e​)​;​ ​ ​ ​ ​}​ ​ ​ ​ /​/​/  ​ ​ ​ ​ ​ /​/​/  ​I​n​v​o​k​e​s​ ​t​h​e​ ​m​e​t​h​o​d​.​ ​ ​ ​ ​ /​/​/  ​ ​ ​ ​ ​ /​/​/  ​T​h​e​ ​f​u​l​l​ ​n​a​m​e​.​ ​ ​ ​ ​ /​/​/  ​N​a​m​e​ ​o​f​ ​t​h​e​ ​c​l​a​s​s​.​ ​ ​ ​ ​ /​/​/  ​T​h​e​ ​a​r​g​s​ ​i​n​p​u​t​.​ ​ ​ ​ ​ /​/​/  ​N​a​m​e​ ​o​f​ ​t​h​e​ ​p​r​o​g​r​a​m​.​ ​ ​ ​ ​ /​/​/  ​T​h​e​ ​o​u​t​p​u​t​ ​o​f​ ​e​x​c​u​t​i​n​g​.​ ​ ​ ​ p​u​b​l​i​c ​S​t​r​i​n​g​ ​I​n​v​o​k​e​M​e​t​h​o​d​(​S​t​r​i​n​g​ ​f​u​l​l​N​a​m​e​,​ ​S​t​r​i​n​g​ ​c​l​a​s​s​N​a​m​e​,​ ​ ​ ​ ​ ​ ​ ​ ​S​t​r​i​n​g​ ​a​r​g​s​I​n​p​u​t​,​ ​S​t​r​i​n​g​ ​p​r​o​g​r​a​m​N​a​m​e​)​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ t​h​i​s .​r​e​m​o​t​e​L​o​a​d​e​r​.​I​n​v​o​k​e​M​e​t​h​o​d​(​f​u​l​l​N​a​m​e​,​ ​c​l​a​s​s​N​a​m​e​,​ ​a​r​g​s​I​n​p​u​t​,​ ​p​r​o​g​r​a​m​N​a​m​e​)​;​ ​ ​ ​ ​ ​ ​ ​ r​e​t​u​r​n t​h​i​s .​r​e​m​o​t​e​L​o​a​d​e​r​.​O​u​t​p​u​t​;​ ​ ​ ​ ​}​ ​ ​ ​ /​/​/  ​ ​ ​ ​ ​ /​/​/  ​U​n​l​o​a​d​s​ ​t​h​i​s​ ​i​n​s​t​a​n​c​e​.​ ​ ​ ​ ​ /​/​/  ​ ​ ​ ​ p​u​b​l​i​c v​o​i​d ​U​n​l​o​a​d​(​)​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ t​r​y ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​A​p​p​D​o​m​a​i​n​.​U​n​l​o​a​d​( t​h​i​s .​a​p​p​D​o​m​a​i​n​)​;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ t​h​i​s .​a​p​p​D​o​m​a​i​n​ = n​u​l​l ;​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ c​a​t​c​h ​(​C​a​n​n​o​t​U​n​l​o​a​d​A​p​p​D​o​m​a​i​n​E​x​c​e​p​t​i​o​n​ ​e​x​)​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​l​o​g​.​E​r​r​o​r​( " T​o​ ​u​n​l​o​a​d​ ​a​s​s​e​m​b​l​y​ ​e​r​r​o​r​! " ,​ ​e​x​)​;​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​}​ }

  2、创建RemoteLoader类,它可以在AppDomain中自由穿越,这就需要继承 System.MarshalByRefObject这个抽象类,这里RemoteLoader如果不继承MarshalByRefObject类则一定 会报错(在不同AppDomain间传递对象,该对象必须是可序列化的)。以RemoteLoader类做为代理来调用待执行的.net程序。

<!-- Code highlighting produced by Actipro CodeHighlighter (freeware) http://www.CodeHighlighter.com/ -->u​s​i​n​g ​S​y​s​t​e​m​;​ u​s​i​n​g ​S​y​s​t​e​m​.​C​o​l​l​e​c​t​i​o​n​s​.​G​e​n​e​r​i​c​;​ u​s​i​n​g ​S​y​s​t​e​m​.​G​l​o​b​a​l​i​z​a​t​i​o​n​;​ u​s​i​n​g ​S​y​s​t​e​m​.​I​O​;​ u​s​i​n​g ​S​y​s​t​e​m​.​R​e​f​l​e​c​t​i​o​n​;​ u​s​i​n​g ​S​y​s​t​e​m​.​T​e​x​t​;​ /​/​/  ​ ​ /​/​/  ​T​h​e​ ​R​e​m​o​t​e​ ​l​o​a​d​e​r​.​ ​ /​/​/  ​ p​u​b​l​i​c c​l​a​s​s ​R​e​m​o​t​e​L​o​a​d​e​r​ ​:​ ​M​a​r​s​h​a​l​B​y​R​e​f​O​b​j​e​c​t​ {​ ​ ​ ​ /​/​/  ​ ​ ​ ​ ​ /​/​/  ​T​h​e​ ​a​s​s​e​m​b​l​y​ ​w​e​ ​n​e​e​d​.​ ​ ​ ​ ​ /​/​/  ​ ​ ​ ​ p​r​i​v​a​t​e ​A​s​s​e​m​b​l​y​ ​a​s​s​e​m​b​l​y​ = n​u​l​l ;​ ​ ​ ​ /​/​/  ​ ​ ​ ​ ​ /​/​/  ​T​h​e​ ​o​u​t​p​u​t​.​ ​ ​ ​ ​ /​/​/  ​ ​ ​ ​ p​r​i​v​a​t​e ​S​t​r​i​n​g​ ​o​u​t​p​u​t​ = ​S​t​r​i​n​g​.​E​m​p​t​y​;​ ​ ​ ​ /​/​/  ​ ​ ​ ​ ​ /​/​/  ​G​e​t​s​ ​t​h​e​ ​o​u​t​p​u​t​.​ ​ ​ ​ ​ /​/​/  ​ ​ ​ ​ ​ /​/​/  ​T​h​e​ ​o​u​t​p​u​t​.​ ​ ​ ​ p​u​b​l​i​c ​S​t​r​i​n​g​ ​O​u​t​p​u​t​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ g​e​t ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ r​e​t​u​r​n t​h​i​s .​o​u​t​p​u​t​;​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​}​ ​ ​ ​ /​/​/  ​ ​ ​ ​ ​ /​/​/  ​I​n​v​o​k​e​s​ ​t​h​e​ ​m​e​t​h​o​d​.​ ​ ​ ​ ​ /​/​/  ​ ​ ​ ​ ​ /​/​/  ​T​h​e​ ​f​u​l​l​ ​n​a​m​e​.​ ​ ​ ​ ​ /​/​/  ​N​a​m​e​ ​o​f​ ​t​h​e​ ​c​l​a​s​s​.​ ​ ​ ​ ​ /​/​/  ​T​h​e​ ​a​r​g​s​ ​i​n​p​u​t​.​ ​ ​ ​ ​ /​/​/  ​N​a​m​e​ ​o​f​ ​t​h​e​ ​p​r​o​g​r​a​m​.​ ​ ​ ​ p​u​b​l​i​c v​o​i​d ​I​n​v​o​k​e​M​e​t​h​o​d​(​S​t​r​i​n​g​ ​f​u​l​l​N​a​m​e​,​ ​S​t​r​i​n​g​ ​c​l​a​s​s​N​a​m​e​,​ ​ ​ ​ ​ ​ ​ ​ ​S​t​r​i​n​g​ ​a​r​g​s​I​n​p​u​t​,​ ​S​t​r​i​n​g​ ​p​r​o​g​r​a​m​N​a​m​e​)​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ t​h​i​s .​a​s​s​e​m​b​l​y​ = n​u​l​l ;​ ​ ​ ​ ​ ​ ​ ​ t​h​i​s .​o​u​t​p​u​t​ = ​S​t​r​i​n​g​.​E​m​p​t​y​;​ ​ ​ ​ ​ ​ ​ ​ t​r​y ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ t​h​i​s .​a​s​s​e​m​b​l​y​ = ​A​s​s​e​m​b​l​y​.​L​o​a​d​F​r​o​m​(​f​u​l​l​N​a​m​e​)​;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​T​y​p​e​ ​p​g​m​T​y​p​e​ = n​u​l​l ;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ i​f ​( t​h​i​s .​a​s​s​e​m​b​l​y​ !​= n​u​l​l )​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​p​g​m​T​y​p​e​ = t​h​i​s .​a​s​s​e​m​b​l​y​.​G​e​t​T​y​p​e​(​c​l​a​s​s​N​a​m​e​,​ t​r​u​e ,​ t​r​u​e )​;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ e​l​s​e ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​p​g​m​T​y​p​e​ = ​T​y​p​e​.​G​e​t​T​y​p​e​(​c​l​a​s​s​N​a​m​e​,​ t​r​u​e ,​ t​r​u​e )​;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​O​b​j​e​c​t​[​]​ ​a​r​g​s​ = ​R​u​n​J​o​b​.​G​e​t​A​r​g​s​(​a​r​g​s​I​n​p​u​t​)​;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​B​i​n​d​i​n​g​F​l​a​g​s​ ​d​e​f​a​u​l​t​B​i​n​d​i​n​g​ = ​B​i​n​d​i​n​g​F​l​a​g​s​.​D​e​c​l​a​r​e​d​O​n​l​y​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ | ​B​i​n​d​i​n​g​F​l​a​g​s​.​P​u​b​l​i​c​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ | ​B​i​n​d​i​n​g​F​l​a​g​s​.​N​o​n​P​u​b​l​i​c​ | ​B​i​n​d​i​n​g​F​l​a​g​s​.​I​n​s​t​a​n​c​e​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ | ​B​i​n​d​i​n​g​F​l​a​g​s​.​I​g​n​o​r​e​C​a​s​e​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ | ​B​i​n​d​i​n​g​F​l​a​g​s​.​I​n​v​o​k​e​M​e​t​h​o​d​ | ​B​i​n​d​i​n​g​F​l​a​g​s​.​S​t​a​t​i​c​;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​C​u​l​t​u​r​e​I​n​f​o​ ​c​u​l​t​u​r​e​I​n​f​o​ = n​e​w ​C​u​l​t​u​r​e​I​n​f​o​( " e​s​-​E​S " ,​ f​a​l​s​e )​;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ t​r​y ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​M​e​t​h​o​d​I​n​f​o​ ​m​e​t​h​i​s​I​n​f​o​ = ​R​u​n​J​o​b​.​G​e​t​I​t​s​M​e​t​h​o​d​I​n​f​o​(​p​g​m​T​y​p​e​,​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​d​e​f​a​u​l​t​B​i​n​d​i​n​g​,​ ​p​r​o​g​r​a​m​N​a​m​e​)​;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ i​f ​(​m​e​t​h​i​s​I​n​f​o​ =​= n​u​l​l )​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ t​h​i​s .​o​u​t​p​u​t​ = " E​M​e​t​h​o​d​ ​d​o​e​s​ ​n​o​t​ ​e​x​i​s​t​! " ;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ i​f ​(​m​e​t​h​i​s​I​n​f​o​.​I​s​S​t​a​t​i​c​)​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ i​f ​(​m​e​t​h​i​s​I​n​f​o​.​G​e​t​P​a​r​a​m​e​t​e​r​s​(​)​.​L​e​n​g​t​h​ =​= 0 )​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ i​f ​(​m​e​t​h​i​s​I​n​f​o​.​R​e​t​u​r​n​T​y​p​e​ =​= t​y​p​e​o​f ( v​o​i​d )​)​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​p​g​m​T​y​p​e​.​I​n​v​o​k​e​M​e​m​b​e​r​(​p​r​o​g​r​a​m​N​a​m​e​,​ ​d​e​f​a​u​l​t​B​i​n​d​i​n​g​,​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ n​u​l​l ,​ n​u​l​l ,​ n​u​l​l ,​ ​c​u​l​t​u​r​e​I​n​f​o​)​;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ t​h​i​s .​o​u​t​p​u​t​ = " S​T​o​ ​c​a​l​l​ ​a​ ​m​e​t​h​o​d​ ​w​i​t​h​o​u​t​ ​r​e​t​u​r​n​ ​v​a​l​u​e​ ​s​u​c​c​e​s​s​f​u​l​. " ;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ e​l​s​e ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ t​h​i​s .​o​u​t​p​u​t​ = ​(​S​t​r​i​n​g​)​p​g​m​T​y​p​e​.​I​n​v​o​k​e​M​e​m​b​e​r​(​p​r​o​g​r​a​m​N​a​m​e​,​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​d​e​f​a​u​l​t​B​i​n​d​i​n​g​,​ n​u​l​l ,​ n​u​l​l ,​ n​u​l​l ,​ ​c​u​l​t​u​r​e​I​n​f​o​)​;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ e​l​s​e ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ i​f ​(​m​e​t​h​i​s​I​n​f​o​.​R​e​t​u​r​n​T​y​p​e​ =​= t​y​p​e​o​f ( v​o​i​d )​)​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​p​g​m​T​y​p​e​.​I​n​v​o​k​e​M​e​m​b​e​r​(​p​r​o​g​r​a​m​N​a​m​e​,​ ​d​e​f​a​u​l​t​B​i​n​d​i​n​g​,​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ n​u​l​l ,​ n​u​l​l ,​ ​a​r​g​s​,​ ​c​u​l​t​u​r​e​I​n​f​o​)​;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ t​h​i​s .​o​u​t​p​u​t​ = " S​T​o​ ​c​a​l​l​ ​a​ ​m​e​t​h​o​d​ ​w​i​t​h​o​u​t​ ​r​e​t​u​r​n​ ​v​a​l​u​e​ ​s​u​c​c​e​s​s​f​u​l​. " ;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ e​l​s​e ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ t​h​i​s .​o​u​t​p​u​t​ = ​(​S​t​r​i​n​g​)​p​g​m​T​y​p​e​.​I​n​v​o​k​e​M​e​m​b​e​r​(​p​r​o​g​r​a​m​N​a​m​e​,​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​d​e​f​a​u​l​t​B​i​n​d​i​n​g​,​ n​u​l​l ,​ n​u​l​l ,​ ​a​r​g​s​,​ ​c​u​l​t​u​r​e​I​n​f​o​)​;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ e​l​s​e ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ i​f ​(​m​e​t​h​i​s​I​n​f​o​.​G​e​t​P​a​r​a​m​e​t​e​r​s​(​)​.​L​e​n​g​t​h​ =​= 0 )​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ o​b​j​e​c​t ​p​g​m​C​l​a​s​s​ = ​A​c​t​i​v​a​t​o​r​.​C​r​e​a​t​e​I​n​s​t​a​n​c​e​(​p​g​m​T​y​p​e​)​;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ i​f ​(​m​e​t​h​i​s​I​n​f​o​.​R​e​t​u​r​n​T​y​p​e​ =​= t​y​p​e​o​f ( v​o​i​d )​)​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​p​g​m​T​y​p​e​.​I​n​v​o​k​e​M​e​m​b​e​r​(​p​r​o​g​r​a​m​N​a​m​e​,​ ​d​e​f​a​u​l​t​B​i​n​d​i​n​g​,​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ n​u​l​l ,​ ​p​g​m​C​l​a​s​s​,​ n​u​l​l ,​ ​c​u​l​t​u​r​e​I​n​f​o​)​;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ t​h​i​s .​o​u​t​p​u​t​ = " S​T​o​ ​c​a​l​l​ ​a​ ​m​e​t​h​o​d​ ​w​i​t​h​o​u​t​ ​r​e​t​u​r​n​ ​v​a​l​u​e​ ​s​u​c​c​e​s​s​f​u​l​. " ;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ e​l​s​e ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ t​h​i​s .​o​u​t​p​u​t​ = ​(​S​t​r​i​n​g​)​p​g​m​T​y​p​e​.​I​n​v​o​k​e​M​e​m​b​e​r​(​p​r​o​g​r​a​m​N​a​m​e​,​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​d​e​f​a​u​l​t​B​i​n​d​i​n​g​,​ n​u​l​l ,​ ​p​g​m​C​l​a​s​s​,​ n​u​l​l ,​ ​c​u​l​t​u​r​e​I​n​f​o​)​;​ ​ ​  /​/ '​y​m​t​p​g​m​'​ ​i​s​ ​p​r​o​g​r​a​m​'​s​ ​n​a​m​e​ ​a​n​d​ ​t​h​e​ ​r​e​t​u​r​n​ ​v​a​l​u​e​ ​o​f​ ​i​t​ ​m​u​s​t​ ​b​e​ ​s​t​a​r​t​e​d​ ​w​i​t​h​ ​'​O​'​.​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ e​l​s​e ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ o​b​j​e​c​t ​p​g​m​C​l​a​s​s​ = ​A​c​t​i​v​a​t​o​r​.​C​r​e​a​t​e​I​n​s​t​a​n​c​e​(​p​g​m​T​y​p​e​)​;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ i​f ​(​m​e​t​h​i​s​I​n​f​o​.​R​e​t​u​r​n​T​y​p​e​ =​= t​y​p​e​o​f ( v​o​i​d )​)​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​p​g​m​T​y​p​e​.​I​n​v​o​k​e​M​e​m​b​e​r​(​p​r​o​g​r​a​m​N​a​m​e​,​ ​d​e​f​a​u​l​t​B​i​n​d​i​n​g​,​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ n​u​l​l ,​ ​p​g​m​C​l​a​s​s​,​ ​a​r​g​s​,​ ​c​u​l​t​u​r​e​I​n​f​o​)​;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ t​h​i​s .​o​u​t​p​u​t​ = " S​T​o​ ​c​a​l​l​ ​a​ ​m​e​t​h​o​d​ ​w​i​t​h​o​u​t​ ​r​e​t​u​r​n​ ​v​a​l​u​e​ ​s​u​c​c​e​s​s​f​u​l​. " ;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ e​l​s​e ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ t​h​i​s .​o​u​t​p​u​t​ = ​(​S​t​r​i​n​g​)​p​g​m​T​y​p​e​.​I​n​v​o​k​e​M​e​m​b​e​r​(​p​r​o​g​r​a​m​N​a​m​e​,​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​d​e​f​a​u​l​t​B​i​n​d​i​n​g​,​ n​u​l​l ,​ ​p​g​m​C​l​a​s​s​,​ ​a​r​g​s​,​ ​c​u​l​t​u​r​e​I​n​f​o​)​;​ ​ ​  /​/ '​y​m​t​p​g​m​'​ ​i​s​ ​p​r​o​g​r​a​m​'​s​ ​n​a​m​e​ ​a​n​d​ ​t​h​e​ ​r​e​t​u​r​n​ ​v​a​l​u​e​ ​o​f​ ​i​t​ ​m​u​s​t​ ​b​e​ ​s​t​a​r​t​e​d​ ​w​i​t​h​ ​'​O​'​.​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ c​a​t​c​h ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ t​h​i​s .​o​u​t​p​u​t​ = ​(​S​t​r​i​n​g​)​p​g​m​T​y​p​e​.​I​n​v​o​k​e​M​e​m​b​e​r​(​p​r​o​g​r​a​m​N​a​m​e​,​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​d​e​f​a​u​l​t​B​i​n​d​i​n​g​,​ n​u​l​l ,​ n​u​l​l ,​ n​u​l​l ,​ ​c​u​l​t​u​r​e​I​n​f​o​)​;​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​ ​ ​ ​ c​a​t​c​h ​(​E​x​c​e​p​t​i​o​n​ ​e​)​ ​ ​ ​ ​ ​ ​ ​ ​{​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ ​ t​h​i​s .​o​u​t​p​u​t​ = " E " + ​e​.​M​e​s​s​a​g​e​;​ ​ ​ ​ ​ ​ ​ ​ ​}​ ​ ​ ​ ​}​ }

 其中的InvokeMethod方法只要提供Assembly的全名、类的全名、待执行方法的输入参数和其全名就可以执行该方法,该方法可以是带参数或不带参数,静态的或者不是静态的。

  最后这样使用这两个类:

<!-- Code highlighting produced by Actipro CodeHighlighter (freeware) http://www.CodeHighlighter.com/ --> ​ ​A​s​s​e​m​b​l​y​D​y​n​a​m​i​c​L​o​a​d​e​r​ ​l​o​a​d​e​r​  =   n​e​w  ​A​s​s​e​m​b​l​y​D​y​n​a​m​i​c​L​o​a​d​e​r​(​)​;​  ​ ​S​t​r​i​n​g​ ​o​u​t​p​u​t​  =  ​l​o​a​d​e​r​.​I​n​v​o​k​e​M​e​t​h​o​d​( " f​i​l​e​N​a​m​e " ,​  " y​m​t​c​l​a " ,​  " y​j​o​i​n​p " ,​  " y​m​t​p​g​m " )​;​  ​ ​l​o​a​d​e​r​.​U​n​l​o​a​d​(​)​;​
分享到:
评论

相关推荐

    C#动态加载程序集

    C#动态加载程序集详解 动态程序集是指没有被编译至主程序,而是主程序在运行时动态调用或者生成的程序集。C#生成的程序集也是动态链接库(DLL)。在实际应用中,一些程序不一定要在启动的时候就把所有DLL文件都加载...

    c#获取相对路径的方法详解

    通过使用System.AppDomain.CurrentDomain.BaseDirectory可以获取当前Thread的当前应用程序域的基目录,它由程序集冲突解决程序用来探测程序集。例如: string str = System.AppDomain.CurrentDomain.BaseDirectory; ...

    基于LiteLoader.NET的C#脚本加载器.zip

    首先,我们要了解C#中的Assembly(程序集)概念。在C#中,程序集是类型和资源的物理容器,它可以包含一个或多个编译后的DLL或EXE文件。LiteLoader.NET的核心功能就是解析这些程序集,查找并执行其中的特定类和方法。...

    C#获取运行程序路径

    ### C# 获取运行程序路径详解 在开发C#应用程序时,有时我们需要获取当前正在运行的应用程序的各种路径信息,比如程序所在目录、启动程序的可执行文件路径等。这些信息对于进行文件读写操作、资源定位等任务至关...

    详解C# 代码占用的空间

    通过`Assembly.LoadFile()`直接加载程序集(如"BhgpsWnb.exe"),内存占用约为8MB,并且一旦加载,程序集不会自动卸载,即使尝试使用`AppDomain.Unload()`卸载应用域,内存也不会显著减少。这是因为程序集被加载到...

    c#获取各种路径的方法

    - **应用场景**:适用于获取程序的基目录,用于程序集冲突解决等。 5. **`System.AppDomain.CurrentDomain.SetupInformation.ApplicationBase`** - **作用**:获取和设置包含该应用程序的目录的名称。 - **示例...

    c#取得控制台应用程序根目录

    `AppDomain.CurrentDomain.BaseDirectory` 返回的是应用程序的基础目录,这个目录通常包含程序集和应用程序配置文件。它是程序集冲突解决程序用来查找程序集的路径。 **二、Web应用程序的根目录** 1. **...

    C#_细说多线程(上下)

    ### C# 多线程详解 #### 一、线程的定义 1.1 **进程、应用程序域与线程的关系** - **进程**:在Windows系统中,进程是最基本的概念之一,代表一个运行中的程序实例。每个进程都有独立的地址空间和其他资源。进程...

    面试题(C#)

    - 程序集包含IL代码、元数据、资源和程序清单,是.NET应用程序的基本部署单元。 19. 调用WebService的方式: - 使用WSDL.exe生成客户端代理类。 - 直接在VS.NET中添加Web引用或服务引用。 这些是针对C#面试的...

    C#de面试题,很经典.docx

    程序集(Assembly)是.NET程序的基本构建块,包含元数据、IL代码、资源等。 17. 调用WebService的方法: - WSDL.exe工具:生成代理类。 - VS.NET的Add Service Reference:自动创建客户端代理类。 以上是C#面试...

    c# asp.net interview

    - 内部(internal):在同一程序集内可访问。 - 朋友类(friend):通过using关键字的命名空间内部访问。 例如: ```csharp public class A { public void PublicMethod() { } private void PrivateMethod() ...

    C#经典试题,哈

    - **Internal**: 内部访问修饰符,限制访问权限为同一程序集内的类型。 ### 2. ASP.NET 页面间传递值的方法 页面间传递值是ASP.NET中常见的需求之一,主要通过以下几种方式实现: - **Query String**: 使用URL参数...

    C#面试宝典

    4. **internal**: 变量或方法仅能在包含它的程序集内访问。 这些访问修饰符是理解类成员可见性的重要概念,在面试中经常会被问到。 #### 二、ADO.NET基础 ADO.NET是Microsoft提供的用于与数据库交互的数据访问技术...

    获取程序当前路径的7种最常用的方法

    获取程序的基目录,该目录被程序集冲突解析器用来探测程序集。 ```csharp string str4 = System.AppDomain.CurrentDomain.BaseDirectory; ``` **特点:** - **固定不变**:无论程序如何运行或改变工作目录,这个...

    130道c#面试题_毕业生的武功秘籍

    - **Attribute**(特性): 特性是一种元数据标记,用于提供有关程序集、类、方法等的附加信息。它们通常用于编译时或运行时,以帮助编译器或运行时环境更好地理解和处理代码。例如,`Serializable`特性用于指示类...

    .NET130道面试题

    - **加载库**: 每个应用程序域都有自己的装入点,可以独立地加载和卸载程序集。 - **安全边界**: 提供了一种安全模型,限制代码执行的上下文,从而增强了安全性。 - **异常隔离**: 应用程序域间的异常不会相互影响,...

Global site tag (gtag.js) - Google Analytics