生活

解析.NET对象的跨应用程序域访问(下篇)生活

24 12月 , 2018  

   
转眼就到了七夕,匆匆忙忙的步履是我们在为生活努力的描绘,新的一年,我们应该大力让祥和有不一致的活着和追求。生命不息,奋斗不止。在上篇博文中最重要介绍了.NET的AppDomain的连带音讯,在本篇博文大校会重要表达.NET程序集、对象代理,以及对象的封送原理。

 
 等待着下元节的过来,过完寒食节,这多少个年也总算过完了,也得起头出去挣钱了,过年回家感觉每个人都觉着很牛,唯有团结太渣,为了制止年初再出现这样难堪的范畴,仍旧需要大力干活。争取当上老总,赢取白富美,走上人生巅峰。(生活需要幻想,也需要面对现实,努力取得一个向上的情感,比起所有财富要尤其的难得。)

一.程序集解析:

   
谈到程序集,就要领悟如何叫做程序集,我们看看程序集的定义是咋样。程序集大体分为二种:一种是类库(就是大家看来的.DLL文件);一种是可执行程序(就是我们看看的.EXE文件)。程序集是一个或三个模块/资源文件的逻辑分组(一个模块成为单模块程序集或者单文件程序集;三个模块成为多模块程序集或者多文件程序集);程序集是重用、安全性以及版本控制的小不点儿单元。程序集的要害结合,请看上边的图示:

生活 1

     
程序集并不一定对应唯一的一个文本,也足以涵盖六个公文,在四个文件组成的次序集中,包含程序集清单的公文称为主模块,每个程序集都必须含有一个主模块,并且唯有一个。对于程序集更是详实的牵线,在另一篇博文中所有介绍,在此间就不在赘述,博文地址:http://www.cnblogs.com/pengze0902/p/6043525.html

  生活 2

二.DotNet的目的代精通析:

   
 对于当今还在聊QQ和看博客的同志们,我只想借用上图问一句“你们不上班么?…哈哈哈…”。好了,不聊天了,起头我们前些天的要旨。

   1.目的代理概述:

     
本文重假使教学对象的跨应用程序域访问,后边介绍了应用程序域和次序集的连带新闻,在此处就要起来上课如何来促成指标的跨应用程序域的访问操作。对象跨应用程序域的操作需要知道代理和封送,代理提供了和长途对象完全相同的接口,代理有着和长距离对象完全等同的接口和名称,对于客户端而言,代理就接近远程对象一样。可是代理并不带有向客户端程序提供劳务的实际代码,代理仅仅是将协调与某一实际目的绑定,然后将客户端对协调的呼吁打包为消息,然后发送给实际目标。

   
 在此地首先介绍一下代理,就需要知道多个名词“透西楚理”和“真实代理”。有如下图所示:

生活 3   
透西夏理是由CLR创制的一种专门对象,首即使为着将艺术调用转换成音信交换。由上图可以看到透玄汉理和真正代理,透南齐理和实事求是代理是逐一对应的涉嫌。透西魏理对象最后必须充当一个特定的项目标实例。

   
一个程序取得透北魏理的引用后,这多少个顺序将在代理对象上行使方式调用。当程序在透大顺理对象上选取方法调用时,CLR将成立一个新的音讯对象以象征那几个调用,CLR会将以此信息传递给真实代理用于拍卖。

   
真实代理将生出此外一条音信,以代表调用的结果,透南宋理将应用第二条音信对这么些调用的对阵举行转发,透明地将结果传送给调用方。假如实际代理重返的响应音讯包含非凡,透南梁理将再也抛出那一个可怜,并再两回将结果传给调用方。

 
 透南宋理和忠实代理之间的音信沟通是因此真正带来的Invoke方法暴发。在透汉代理对象上的章程调用,导致从基于堆栈处理的信息转换为基于新闻处理的艺术。再回去响应音信在此以前,真实代理的Invoke实现可能将新闻分发给其他数据的拍卖节点,为了传送调用到的一个实际目的,最后的拍卖节点归根结蒂都急需将呼吁音信转换为堆栈帧。 
   

   
 C#的连串中,大家掌握最多的就是静态类,对于静态类的有的特性在此地就不做牵线了,因为对此一个.NET开发者来说,静态类的片段风味应该是有早晚的支配,并且在项目中行使的也是非凡多。现在需要介绍的是另一种档次,这就是“分部类型”,对于“分部类型”的问询,很两个人臆度也就是通晓而已,接下去就让我们一道来上学一个“分部类型”这一C#的语言特点。

   2.对象代理原理分析:

        上边根本介绍了代办的有些为主理论,上面看一下这个核心目的。

    (1).RealProxy.GetTransparentProxy():重返 RealProxy
的当下实例的晶莹代理。  

  public virtual object GetTransparentProxy()
    {
      return this._tp;
    }

     
 该模式在System.Runtime.Remoting.Proxies命名空间下,RealProxy类:提供代理的基本功能。

    (2).ProxyAttribute.CreateProxy():成立由指定的
ObjRef描述并置身服务器上的远程对象的远程处理代理的实例。 

[SecurityCritical]
    public virtual RealProxy CreateProxy(ObjRef objRef, Type serverType, object serverObject, Context serverContext)
    {
      RemotingProxy remotingProxy = new RemotingProxy(serverType);
      if (serverContext != null)
        RealProxy.SetStubData((RealProxy) remotingProxy, (object) serverContext.InternalContextID);
      if (objRef != null && objRef.GetServerIdentity().IsAllocated)
        remotingProxy.SetSrvInfo(objRef.GetServerIdentity(), objRef.GetDomainID());
      remotingProxy.Initialized = true;
      Type type = serverType;
      if (!type.IsContextful && !type.IsMarshalByRef && serverContext != null)
        throw new RemotingException(Environment.GetResourceString("Remoting_Activation_MBR_ProxyAttribute"));
      return (RealProxy) remotingProxy;
    }

 
 该办法在 System.Runtime.Remoting.Proxies命名空间下,ProxyAttribute类指示对象类型需要自定义代理。该模式接收5个参数,objRef:对要为其创立代理的远程对象的对象引用;serverType:远程对象所在的服务器的体系;serverObject:服务器对象;serverContext:服务器对象所在的上下文。该模式在指定的
<see cref=”T:System.Runtime.Remoting.ObjRef”/>
中表明的远程对象的长途处理代理的新实例。

   
(3).RemotingService(Service)s:提供多种使用和布告远程对象及代理的不二法门。此类无法被接续。

       GetRealProxy()方法再次回到指定透汉朝理前面的实在代理。

 [SecurityCritical]
    [ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)]
    [MethodImpl(MethodImplOptions.InternalCall)]
    public static extern RealProxy GetRealProxy(object proxy);

   
 该模式接收参数,proxy:一个透北宋理。该方法再次回到透北齐理前边的真实性代理实例。

   
 IsTransparentProxy()方法再次来到一个布尔值,该值提示给定的靶子是晶莹剔透代理依旧实际目标。

[SecuritySafeCritical]
    [ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)]
    [MethodImpl(MethodImplOptions.InternalCall)]
    public static extern bool IsTransparentProxy(object proxy);

   
该格局接收一个参数,proxy:参数对要检查的目的的引用。该办法再次回到指定的靶子是晶莹剔透代理还是实际目标。

   ExecuteMessage():连接到指定的长途对象,并对其举办提供的 <see
cref=”T:System.Runtime.Remoting.Messaging.IMethodCallMessage”/>。

  [SecurityCritical]
    public static IMethodReturnMessage ExecuteMessage(MarshalByRefObject target, IMethodCallMessage reqMsg)
    {
      if (target == null)
        throw new ArgumentNullException("target");
      RealProxy realProxy = RemotingServices.GetRealProxy((object) target);
      if (realProxy is RemotingProxy && !realProxy.DoContextsMatch())
        throw new RemotingException(Environment.GetResourceString("Remoting_Proxy_WrongContext"));
      return (IMethodReturnMessage) new StackBuilderSink(target).SyncProcessMessage((IMessage) reqMsg);
    }

   
该方法接收多少个参数,target:要调用其艺术的长途对象。reqMsg:指定的中远距离对象的主意的主意调用音讯。该形式知识简单地为对象对象创设一个堆栈生成器,并且发送一个信息给这些接收器。堆栈生成器接收器处理底层的仓库操作,并且调用实际的不二法门。当方法终止时,堆栈生成器接收器把作为结果的堆栈帧转换为响应的音信,CLR用它看成该办法调用的结果再次来到。

一.C#分部类型和分部方法分析:

三.DotNet的目标封送解析:

   
 下边介绍了代办,下边简单的牵线一下目标的封送,对象的封送分为三种,第一种为传值封送;第二种为传引用封送。
  

   1.分部类型概述:

   
 学习“分部类型”,我们仍旧先来打探一下怎么样叫做“分部类型”。分部类型是指可以在四个源文件中为一个类型编写代码。对于分部类型的施用情形,使用最多的地方是一些代码是自动生成,而其它部分的代码为手写的类型。“分部类型”是由C#2.0时引入的。在继承链上设有一个不必要的链接,会引发某些问题或下降封装型。

   
 大家前几日对此分部类型的定义有一个大约的精晓,以及对分部类型的应用场景也有一个起先的垂询,接下去大家来看一下怎么着创立分部类型和分部类型的施用模式。

   1.传值封送:

     
当位于A应用程序域的对象传递给B应用程序域,.NET将A中目的的意况举行复制、体系化、然后在B中再一次成立,并由此代理对象开展访问。

生活 4

生活 5

                     (1 传值封送)                                      
                    (2 传引用封送)

   2.分部品类的创制和采纳情势:

     
 假诺急需创制分部类型,大家只需要在事关的各种文件的类其它扬言部分添加一个上下文关键字partial。对于分部类型,编译器在编译以前就把具有的公文合并在一起了。在一个文本中代码可以调用其余一个文本中的代码。有如下代码:

   SegmentType1.cs:

 partial class SegmentType
    {
        private void Add()
        {
            Update();
        }

        private void Delete()
        {
        }
    }

 SegmentType2.cs

  partial class SegmentType
    {
        private void Update()
        {
            Delete();
        }
    }

   
以上是对分部类型做了一个简单的阐发和拔取,这多少个.CS文件在编译器编译往日就曾经统一在一道了。对于分部类型不可能在一个文本中编辑成员的一半代码,而把此外一半代码放到其余一个文书中,必须确保每个独立的积极分子必须完整地位于它所处的文书中。如下代码:

  SegmentType1.cs:

    partial class SegmentType
    {
        private void Add(string fileName)
        {
            FileStream fs = null;
            try
            {
                fs = File.Create(fileName);
            }           
        }
    }

SegmentType2.cs

 partial class SegmentType
    {
        private void Update()
        {
            Add();
            catch (ArgumentException arex)
            {
                throw arex;
            }
            finally
            {
                if (fs != null)
                {
                    fs.Close();
                    fs.Dispose();
                }
            }
        }
    }

   上边演示的做法是不可以通过编译的。

 
 对于项目标注明还有部分范围,这就是声称必须要相互匹配,任何文件都能指定要贯彻的接口和基类型,以及项目参数的羁绊。如若两个公文都设定了基类型,那么它们必须是千篇一律的,并且只要四个文本都设定了花色参数约束,那么约束必须是均等的。有如下代码实例:

  SegmentType1.cs:

    //接口约束:IEquatable<string>;
    //where TFirst:class :和类型参数约束
    partial class SegmentType<TFirst,TSecond>:IEquatable<string> where TFirst:class 
    {
        //实现IEquatable<string>接口方法
        public bool Equals(string other)
        {
            return false;
        }
    }

SegmentType2.cs

    //指定基类:EventArgs
    //指定接口:IDisposable
    partial class SegmentType<TFirst, TSecond> :EventArgs,IDisposable
    {
        //实现方法
        public void Dispose()
        {
        }
    }

  以上的接口和基类约束中,也可以选择如下方法:

 SegmentType1.cs:

    //接口约束:IEquatable<string>;
    //where TFirst:class :和类型参数约束
    partial class SegmentType<TFirst,TSecond>:IEquatable<string> where TFirst:class 
    {
        //实现方法
        public void Dispose()
        {
        }
    }

SegmentType2.cs

    //指定基类:EventArgs
    //指定接口:IDisposable
    partial class SegmentType<TFirst, TSecond> :EventArgs,IDisposable
    {
        //实现IEquatable<string>接口方法
        public bool Equals(string other)
        {
            return false;
        }
    }

 
 对于接口和基类型约束可以拓展置换,基于这种特点,可以将点名的接口与落实分离,将为不同档次变更相同的签名的艺术封装到一个接口中。不能在宣称类型时指定其促成了该接口。

 
 以上是重中之重教学了分部类型的创始和动用方法,接下去大家再来精通一下分部方法的连带知识。

2.传引用封送:

     
传引用封送的布局如上图所示,当客户端在代理调用方法时,由代理将对章程的乞请发送给远程对象,远程对象执行措施请求,最终再将结果传到给客户端,这种格局叫做传引用封送。传引用封送分为二种不同的法门,分为客户端激活(Client
Activated)、服务端激活Singleton(Server Activated
Singleton)、服务端激活SingleCall(Server Activated
SingleCall)。两种艺术的联手特征,服务对象创设且平素维持在宿主应用程序中。

   传引用封送的方法在这边就不做详细介绍了。

 3.分部方法分析:

 
 对于分部方法的相干概念,在前头介绍分部类型时曾经做了介绍,分部方法的创始和利用与分部类型类似。分部方法有一个特点:任何对未兑现的分部方法的调用,都会被编译器移除。

 
分部方法的讲明与纸上谈兵方法的表明类似,只需要使用partial修饰符提供签名而无须任何实现。实现也亟需partial修饰符举办修饰。有如下代码:

 SegmentType1.cs:

 partial class SegmentType
    {
        public SegmentType()
        {
            SegmentTypeStart();
            Console.WriteLine("分部方法解析...");
            SegmentTypeEnd();
        }

        partial void SegmentTypeStart();

        partial void SegmentTypeEnd();
    }

SegmentType2.cs

  partial class SegmentType
    {
        partial void SegmentTypeStart()
        {
            Console.WriteLine("分部方法开始...");
        }
    }

 
 在分部方法中,由于方法可能不存在,所以分部方法再次来到类型必须声明为void,且不可以获取out参数。分部方法必须是个体的,可是是静态的可能泛型。

二.C#分部类型和分部方法的特征:

 
 下边介绍了分部类型和分部方法的定义、创造和使用办法,在这边根本介绍一下分部方法和分部类型的特征。分部类型首要连接设计器和任何代码生成器。利用分部类型模型,代码生成器可以拥有自由的操作文件,或者只要它愿意可以每回都重写整个文件。

 
 某些代码生成器仍是可以够采纳不扭转任何C#文本,而是等到构建举行的时候再生成。代码生成器的运用相比的大面积,比如Web服务器代理、ORM工具生成配置文件等等。对于在ORM工具的接纳有如下图:

   生活 6

 
 分部类型在其他地点也有相比较多的施用,分部类型可以协助我们开展重构。(重构的率先步就是将相比大的品类分成较小的类,很多的涉嫌的内容首先就足以分开为在五个或多少个文本上存放的分部类型。)

   分部类型也得以帮衬我们进单元测试。

 
 分部方法能在手动创造的文本中指定某种行为,并在自动生成的公文中选取该表现。

四.总结:

    对象的跨应用程序域方法的问题就介绍这么多,希望对大家持有补助。

三.C#分部类型实例:

 
 分部类型和分部方法是一个言语特色,在这里给出一个利用了分部类型的品类。https://github.com/fiidau/Phasing-Utility

四.总结:

   
 对于分部类型和分部方法的介绍还有许多,在本文中只是做了一个简约的牵线,分布类型的行使也是比较的大面积,可以大幅度的晋级我们的代码质量。希望本文对我们有所帮忙。


相关文章

发表评论

电子邮件地址不会被公开。 必填项已用*标注

网站地图xml地图