.NET简谈组件程序设计之(delegate与event关系)

 本人最近一段时间在学习关于.NET组件编程方面的技术,在学习过程中确实有很多好的东西需要与大家分享。[王清培版权所有,转载请给出署名]

关于什么叫组件编程,其实就是利用.NET来开发基于组件模型的程序,面向组件编程而非面向对象编程,这是一个高度,没有很长时间的学习与磨练

是体会不到这个感觉的。我们现在的开发思想应该是以面向对象为主的,但是如何提升这个高度,只有慢慢的学习了。

其实面向组件编程包含了面向对象编程思想,将一组功能独立的封装起来供以后重复使用,但是在开发组件的过程中需要使用到面向对象的思想来构

造组件,这两个概念不矛盾,面向对象思想是具体实现,而面向组件思想应该说是站在一个产品或者说是一个框架的高度来宏观的形容。

这些技术哲学我们就不讨论了,学点实际的东西比较现实。我们只需要知道,面向对象编程是代码重用,而面向组件编程是实现的重用。而不管是面

向对象也好还是面向组件也好,归根到底都得用良好的代码来实现。只要我们在开始编码的时候,在脑海里注入这些需要考虑的想法后就可以了。

这篇文章我们先来扫除组件编程中经常用到的委托与事件的一些技术疑惑。在没有学习组件编程之前,我也是不能理解delegate与event的关系和两

者之间到用意何在。但是在最近的学习过程中以有了大概的了解,并且决定写出学习到的技术与大家分享。[王清培版权所有,转载请给出署名]

delegate在C#中表示委托的概念,而event表示事件的概念,但是这两者之间为什么需要结合起来使用,不用event也能很好的实现面向对象中的事件

的思想和功能,通过多播委托一样可以调用所有订阅者。

其实要说为什么需要用event来使用事件的机制,一句话就概括了,但是我这里先不说,说了就没啥意思了,请继续看。

我们先来看点代码:

1:

using System;
using System.Collections.Generic;
using System.Text;

namespace EventDemo
{
    /// <summary>
    /// 句柄移除委托
    /// </summary>
    /// <param name="handle">提示信息</param>
    public delegate void MoveHandler(string handle);
    /// <summary>
    /// 句柄对象
    /// </summary>
    public class ObjectHandler
    {
        /// <summary>
        /// 句柄事件
        /// </summary>
        public MoveHandler hand;
        /// <summary>
        /// 触发句柄事件通知所有订阅者
        /// </summary>
        public void Onhand()
        {
            hand("句柄事件");
        }
    }
}

 2

using System;
using System.Collections.Generic;
using System.Text;

namespace EventDemo
{
    class Program
    {
        static void Main(string[] args)
        {
            ObjectHandler handermanager = new ObjectHandler();
            handermanager.hand += handmethod;
            handermanager.Onhand();
        }
        public static void handmethod(string eventstring)
        {
            Console.WriteLine(eventstring);
            Console.ReadLine();
        }
    }
}

 为了演示效果,我随便起了个对象名称,没有什么特殊意义。

我定义了一个ObjectHandler对象,在内部使用MoveHandler委托实例表示事件对象,当调用Onhand方法的时候我通过委托实例来逐一的调用订阅者来达到事件的效果。但是一般不回将触发事件的方法定义成公共的,这里只是为了显示。

[王清培版权所有,转载请给出署名]
我们引入问题,事件是属于对象内部私有的,只能由对象来触发事件才符合面向对象规则,但是光使用委托无法达到目的。委托实例需要被订阅者订阅才行,那么委托实例必须是公共的,这个时候委托就不可能保证是谁触发了事件。
请看代码:

3:

using System;
using System.Collections.Generic;
using System.Text;

namespace EventDemo
{
    class Program
    {
        static void Main(string[] args)
        {
            ObjectHandler handermanager = new ObjectHandler();
            handermanager.hand += handmethod;
            handermanager.Onhand();
            /*我通过触发对象内部的委托,来蒙骗所有订阅者。
             * 订阅者都认为是ObjectHandler发出的事件,其实是有人偷偷的模拟事件。*/
            handermanager.hand("借刀杀人");
        }
        public static void handmethod(string eventstring)
        {
            Console.WriteLine(eventstring);
            Console.ReadLine();
        }
    }
}

订阅者没有任何理由来承担这个意外的责任,ObjectHandler对象必须为此承担责任。

那么如何避免事件不被恶意者触发呢,那么这个是就需要event关键字了,如果用event修饰过后的委托实例,是无法在对象的外部被触发的。请看代码:

4:

using System;
using System.Collections.Generic;
using System.Text;

namespace EventDemo
{
    /// <summary>
    /// 句柄移除委托
    /// </summary>
    /// <param name="handle">提示信息</param>
    public delegate void MoveHandler(string handle);
    /// <summary>
    /// 句柄对象
    /// </summary>
    public class ObjectHandler
    {
        /// <summary>
        /// 句柄事件
        /// </summary>
        public event MoveHandler hand;
        /// <summary>
        /// 触发句柄事件通知所有订阅者
        /// </summary>
        public void Onhand()
        {
            hand("句柄事件");
        }
    }
}

 

 这样就很好的维护了对象的封闭原则。

下一篇我们将学习委托的更深层次的应用"异步委托" 

时间: 2024-10-25 03:00:54

.NET简谈组件程序设计之(delegate与event关系)的相关文章

.NET简谈组件程序设计之(初识.NET线程Thread)

由于多线程的内容比较多我会用几篇文章来讲解. 多线程在我们日常开发过程中用的很多,上一篇".NET简谈组件程序设计之(异步委托) "详细的讲解了基于委托的多线程使用,委托是基于后台线程池的原理,这篇文章将主要介绍直接使用Thread对象来实现多线程. 当然使用Thread没有使用Delegate那么容易,毕竟多线程跟异步调用是两个相差很大的技术方向,我也是略懂点皮毛,在此献丑给大家,如有讲的不对的地方还请指出.[王清培版权所有,转载请给出署名] 我们先来理解几个概念,以方便我们学习.

.NET简谈组件程序设计之(渗入序列化过程)

在本人的上一篇文章".NET简谈组件程序设计之(初识序列化.持久化) "中,我们基本上了解了什么叫序列化和持久化.通过系统为我们提供的服务,我们可以很方便的进行二进制序列化.SOAP协议序列化. 今天这篇文章是来讲解怎么运用一些高级的功能,在序列化.反序列化过程中进行一些控制.[王清培版权所有,转载请给出署名] 这里穿插一句题外话:其实在我们自己编写组件的时候真的有好多东西可以借鉴.NET平台的一些优点,它的功能都不是死的,可以订阅.可以切入,在我们编写组件的时候,我们其实也要好好考虑

.NET简谈组件程序设计之(初识NetRemoting)

在本人的".NET简谈组件程序设计之(初识远程调用)  "一文中,我们了解到什么是远程调用或者说在.NET平台上远程调用是什么样子的,可能和偏低层(Socket\Rpc)的远程调用有点距离.这只是系统为我们封装了假象而已,看不见不代表没有这逻辑,是为我们减轻了劳动负担.[王清培版权所有,转载请给出署名] 这篇文章我们来简单的了解一下在.NET平台上有一个强有力的远程调用武器,也是上一篇文章中我一笔带过的远程英雄.NetRemoting. 其实在.NET平台里面到处都能看见Remotin

.NET简谈组件程序设计之(上下文与同步域)

我们继续学习.NET多线程技术,这篇文章的内容可能有点复杂.在打破常理之后,换一种新的思考模型最为头疼.这篇文章里面会涉及到一些不太常见的概念,比如:上下文.同步域等等.我也是最近才接触这些关于组件编程方面的高深技术,大家一起学习,再大的困难也是有时间限制的,只要我们坚持. 在本人的上一篇文章".NET简谈组件程序设计之(多线程与并发管理一)"中,只是初步的带领我们学习一下关于多线程的一些基本的原理,包括线程切换,线程的开始.执行.等待.结束. 这篇文章的重点是学习关于线程的同步.互斥

.NET简谈组件程序设计之(初识远程调用)

在.NET1.0版本出来的时候,要想进行远程调用基本上都是通过WebService的方式.而随着.NET2.0版本的出现,我们可以通过一个更加方便且高扩展性的框架来进行编写远程调用的程序,也就是我们都比较熟悉的.NetRemoting. 网上对.NetRemoting技术讲解的文章不计其数,但是很少有一本比较全面的.系统的学习书籍.我们都是从哪些零散的知识里慢慢摸索,效果不太理想. 今天我也来简单的介绍一下我理解的Remoting.不仔细研究一下还真不知道它的厉害,完全的托管平台.高扩展性.灵活

.NET简谈组件程序设计之(手动同步)

在上一篇文章".NET简谈组件程序设计之(上下文与同步域)"中,我们学习了关于一些上下文和同步域的概念,可以利用这两个技术来进行自动同步. 今天我们主要学习怎么手动来执行同步,能从更小的粒度进行封锁,以达到最大程度的吞吐量.[王清培版权所有,转载请给出署名] 我们知道线程是进程的运行实体,进程是资源分配单位,而线程是执行单位.照书上所说,线程是程序的执行路径,当我们分配一个线程的时候,要确定线程的执行路径是什么,也就是代码中的ThreadStart委托所指向的入口点方法. 一旦我们手动

.NET简谈组件程序设计之(初识序列化、持久化)

 今天我们来学习在组件开发中经常用到的也是比较重要的技术"序列化". 序列化这个名词对初学者来说不太容易理解,有点抽象.我们还是用传统的分词解释吧,肯定能搞懂它的用意是什么. 解释:数学上,序列是被排成一列的对象(或事件):这样,每个元素不是在其他元素之前,就是在其他元素之后.这里,元素之间的顺序非常重要. 那么我们对照这样的解释来分析一下我们程序中的序列化什么意思.都知道对象的状态是在内存中实时存着的,对象的状态在初始化的时候是通过系统分配的,在后期的程序运行过程中可能对它进行过一些

.NET简谈组件程序设计之(详解NetRemoting结构)

在本人的上一篇文章中只是简单的介绍了一下.NETRemoting的一般概念和基本的使用.这篇文章我想通过自己的学习和理解将对.NETRemoting的整体的一个框架进行通俗的讲解,其中最重要的就是信道(管道)处理模型思想,这里面蕴含了很多的设计原理.[王清培版权所有,转载请给出署名].NETRemoting远程处理架构是一个半成品,是.NET给我们的扩展框架,要想用于商业项目必须进行一些安全.性能方面的控制.要想进行一定深度的扩展那就要必须了解它的整体结构,各个点之间的关系才能很好的控制它. 网

.NET简谈组件程序设计之(AppDomain应用程序域)

最近在苦学.NET底层框架模型,发现.NET深入真的不是一般的难,不开源.没有相关系统的官方的书籍做学习资料,只能零散的看MSDN.要想摸熟.NET的模型真的并非易事.慢慢来吧.[王清培版权所有,转载请给出署名] .NET应用程序域(AppDomain)是我们所有.NET应用程序的逻辑宿主容器.初次接触会感觉到AppDomain离我们日常开发比较远,不常用到.其实是我们很少接触一些复杂而底层的系统结构.在日常的开发中,我们多数是基于数据库的管理信息系统(MIS),做增.删.改.查的操作.我始终认