C#中事件的使用
C#中事件的使用
用一个例子来说明事件的使用。
创建一个简单的类,名为FileWatch,包含事件OnfileChange。该类将检查在执行应用程序的目录(当前
目录,通常是项目名/bin/debug)下,是否存在文件test.txt。如果文件被删除或创建,都将触发事件。
同时提供一个方法MonitorFile以不断地查询该文件。
方法:
在创建一个可用事件之前,首先声明一个委托,放在类的外面。
public delegate void FileWatchEventHandler(object sender,EventArgs e);
接下来创建类FileWatch。然后声明事件,注意事件的类型即为我们之前定义的委托。
public event FileWatchEventHandler FileWatchEvent;
现在创建方法OnFileChange(),当调用该方法时将触发事件:
protected virtual void OnFileChange(EventArgs e)
{
if (FileWatchEvent!=null)
{
FileWatchEvent(this,e);
}
}
最后,创建方法MonitorFile(),
public void MonitorFile()
{
bool bCurrentStatus;
while(true)
{
bCurrentStatus = File.Exists("test.txt");
if (bCurrentStatus != _bLastStatus) //_bLastStatus为私有字段,初始值为false;
{
_bLastStatus = bCurrentStatus;
OnFileChange(EventArgs.Empty);
}
Thread.Sleep(250);
}
}
完整代码如下:
using System;
using System.Threading;
using System.IO;
namespace Sample.Event
{
public delegate void FileWatchEventHandler(object sender, EventArgs e);
public class FileWatch
{
private bool _bLastStatus = false;
public FileWatch()
{
//
// TODO: 在此处添加构造函数逻辑
//
}
public event FileWatchEventHandler FileWatchEvent;
protected virtual void OnFileChange(EventArgs e)
{
if (FileWatchEvent != null)
{
FileWatchEvent(this, e);
}
}
public void MonitorFile()
{
bool bCurrentStatus;
while(true)
{
bCurrentStatus = File.Exists("test.txt");
//状态不符,说明文件被删除或重新创建,此时触发事件;
if ( bCurrentStatus != _bLastStatus )
{
_bLastStatus = bCurrentStatus;
OnFileChange( EventArgs.Empty );
}
Thread.Sleep(250);
}
}
}
}
使用:创建一个Windows应用程序来测试我们之前建立的FileWatch中的事件。首先将刚才创建的项目编译
,生成Assembly:FileWatch.dll,然后添加引用。当然直接添加项目引用也可以。然后在Windows应用程
序中加入命名空间:
using Sample.Event;
然后在应用程序类中,定义一个私有字段,类型为我们之前创建的类FileWatch:
public class frmMain : System.Windows.Forms.Form
{
private Sample.Event.FileWatch FileWatchEventSource;
并在构造函数中实例化该对象;
public frmMain()
{
InitializeComponent();
FileWatchEventSource = new Sample.Event.FileWatch();
然后将本地方法OnFileChange连接到事件中:
FileWatchEventSource.FileWatchEvent+=new Sample.Event.FileWatchEventHandler(OnFileChange);
我们需要调用MonitorFile方法来触发事件。在本例中,我们用线程来控制MonitorFile方法。这样可以在
应用程序闲置的时候运行该方法以触发事件。
thrd = new Thread(new ThreadStart(FileWatchEventSource.MonitorFile));
thrd.Start();
最后,我们需要知道事件是否被触发,为了记录下事件触发的历史记录,我们在ListBox控件添加触发内
容。由于事件触发后调用的方法是OnFileChange,因此我们将操作放在该方法里:
private void OnFileChange(object Sender, EventArgs e)
{
listBox.Items.Add(DateTime.Now.ToString()+": 文件发生改变.");
}
当触发事件时,EventHanler会传递sender和EventArgs类的引用。EventArgs类通常是在事件源和触发事
件器之间传递信息。在本例中,没有传递信息,也没有用到EventArgs类。而只是将事件添加到了ListBox
中。
运行结果如下:

结论:在C#中使用事件的要点:
首先,要建立委托,格式为:
public delegate void 委托名(object sender, EventArgs e);
注意:委托即C里的函数指针,在事件中由于要传递事件及触发事件的对象的信息,因此参数表是固定的。委托名一般格式是:名字+EnvenHandle。这样取名比较规范。
然后,建立一个事件字段:
public event 委托类型 事件名;
注意:event关键字代表事件,返回类型为委托;
再定义一个方法,处理事件,再本例中为OnFileChange(EventArgs e)。在该方法中应该调用事件:
事件名(object ,EventArgs);
这里object一般为本身,实参应为this,EventArgs应为OnFileChange中传递过来的实参,尤其是要传递事件的值。
最后还要创建触发事件的方法。例子中为MonitorFile(),在其方法中,当条件满足则调用OnFileChange来达到触发事件的目的。
再使用事件时,通常要定义两个方法,一个是和事件定义的委托签名一致的方法,在本例中为OnFileChange(Object sender,EventArgs e);
注意在例子中,窗体类的OnFileChange和事件类的OnFileChange是不同的。后者用于调用事件,前者则用于绑定事件。绑定事件的方法很简单,用+=表示添加事件,-=表示删除事件。
例子中
FileWatchEventSource.FileWatchEvent+=new Sample.Event.FileWatchEventHandler(OnFileChange);
即为添加事件。
例子中:首先线程启动(thd.Start()),然后调用MonitorFile()方法。引起事件产生,FileWatchEvent产生后,由于我们将事件FileWatchEvent绑定到了OnFileChange()方法上。因而调用本地即窗口类的OnFileChange()方法,从而实现在ListBox中添加信息。
C#中事件的使用的更多相关文章
- C#中事件的继承
C#中的子类无法调用父类的事件,可以通过在父类中创建一个方法来调用父类的事件,而子类通过调用父类的方法来触发事件. class parent { protected string name; publ ...
- 关于JAVA中事件分发和监听机制实现的代码实例-绝对原创实用
http://blog.csdn.net/5iasp/article/details/37054171 文章标题:关于JAVA中事件分发和监听机制实现的代码实例 文章地址: http://blog.c ...
- DOM中事件绑定补充方法
先将上一篇文章中提到的为元素增加事件的方法和移除事件的方法拿过来: <span style="font-size:18px;">//跨浏览器添加事件 function ...
- 转载:C#中事件和委托的编译代码
接上文转载:C#中事件的由来,这时候,我们注释掉编译错误的行,然后重新进行编译,再借助Reflactor来对 event的声明语句做一探究,看看为什么会发生这样的错误: public event Gr ...
- Qt中事件分发源代码剖析(一共8个步骤,顺序非常清楚:全局的事件过滤器,再传递给目标对象的事件过滤器,最终传递给目标对象)
Qt中事件分发源代码剖析 Qt中事件传递顺序: 在一个应该程序中,会进入一个事件循环,接受系统产生的事件,并且进行分发,这些都是在exec中进行的.下面举例说明: 1)首先看看下面一段示例代码: in ...
- WinForm中 事件 委托 多线程的应用
WinForm中 事件 委托 多线程的应用[以一个下载进度条为例] 第一步:首先我们创建一个winfor的项目 第二步:我们建一个窗体在一个窗体里面 打开一个另外的窗体 另外的窗体有一个按钮 点击后就 ...
- JS中事件绑定的三种方式
以下是搜集的在JS中事件绑定的三种方式. 1. HTML onclick attribute <button type="button" id="upl ...
- Android与javascript中事件分发机制的简单比较
在前面两篇博客中,我们讨论了Android中的事件分发的相关内容,那么在本篇博客当中,我们就简单探讨一下html或javascript中的事件分发机制,并进行简单的对比. 在前端中,对事件进行绑定有三 ...
- Qt中事件分发源代码剖析
Qt中事件分发源代码剖析 Qt中事件传递顺序: 在一个应该程序中,会进入一个事件循环,接受系统产生的事件,并且进行分发,这些都是在exec中进行的. 下面举例说明: 1)首先看看下面一段示例代码: i ...
随机推荐
- 解决npm install缓慢
http://npm.taobao.org/ 使用淘宝提供的cnpm替代npm
- 6 this的使用方法
class Person { String name; void talk() { System.out.println("my name is "+this.name); } } ...
- 【Codeforces 707B】Bakery 水题
对每个storages找一下最短的相邻边 #include <cstdio> #define N 100005 #define inf 0x3f3f3f3f using namespace ...
- ioc和aop的理解(Spring就是一个轻量级的控制反转(IoC)和面向切面(AOP)的容器框架。)
IoC,(Inverse of Control)控制反转,其包含两个内容:其一是控制,其二是反转.在程序中,被调用类的选择控制权从调用它的类中移除,转交给第三方裁决.这个第三方指的就是Spring的容 ...
- 安装vmall5:从ebak恢复数据,需要配置php.ini
上传vmall5源码到服务器后访问ebak目录,发现网页不显示.用xshell登录到服务器手动执行ebak/index.php查看输出,发现这样一个错误: PHP Parse Error: synta ...
- gulp用途
前端构建工具,可以实现文件合并.文件压缩.语法检查.监听文件变化 参看: http://blog.sina.com.cn/s/blog_6592d8070102vmuq.html https://se ...
- poj 1269 线段相交/平行
模板题 注意原题中说的线段其实要当成没有端点的直线.被坑了= = #include <cmath> #include <cstdio> #include <iostrea ...
- Windows Directory ACL Security Check By ACL Baseline
catalog . Windows NTFS ACL(MAC) Permission . How the System Uses ACLs . 服务器不安全ACL配置带来的攻击向量 . NTFS AC ...
- Database(Mysql、Sqlserver) Configuration Security Reinforcement
目录 . 引言 . Mysql . Sqlserver 1. 引言 黑客获取了数据库的帐号密码之后,就可以通过Database Client登录数据库,利用SQL指令.数据库指令执行组件进行进一步的提 ...
- 电影发烧友必备知识-720P、1080P、4K的区别
随着技术的进步,现在的影视作品的清晰度也越来越高,观众的体验也越来越好,普清的电影基本没人看了,尤其是影视爱好者现在都是看1080P或蓝光原盘.4K. 目前主流清晰度主要分为720P(高清).1080 ...