对c#下函数,委托,事件的一点理解!_c#应用
2008-02-23 05:42:16来源:互联网 阅读 ()
今天一来是有点空,二来是在博客上偶然看到有关于委托的文章,一时兴起,就自己也写一点心得和大家分享一下。
先看一个例子:
using System;
namespace ConsoleApplication1
{
class Class1
{
[STAThread]
static void Main(string[] args)
{
bool m_isRight = false;
object m_obj = m_isRight?MyWrite("true"):MyWrite("false");
Console.Write(m_obj);
}
static private int MyWrite(object i_string)
{
Console.Write(i_string);
return i_string.ToString().Length;
}
}
}
问输出的结果是什么?有一个刚学习程式设计不久的学生的回答是:false false
这个结果给我的映像很深,为什么呢?因为我觉得这个不但仅是学生的一个错误,而更多的是这个学生深入的思考了问题。
因为m_obj是个对象,所以这个学生理解为:MyWrite()这个函数对象能够直接赋值给m_obj,然后m_obj就当成MyWrite()这个函数来调用,所以他就认为:
Console.Write (m_obj); 等于是:Console.Write (MyWrite(“false”));
这是思维是很有创意的,不是吗?
于是就是C#里而很多人不好理解的委托了。其实,从使用上讲,他就是个函数变量!如上面的例子,假如真的是想把MyWrite()做为对象赋值给m_obj会是个什么结果呢?
我觉得我们先得解决以下几个问题,才能正确的把函数当成变量赋值给一个对象:
1、假如能够给一个对象赋函数值,如何来区别不同的函数?
2、如何区别他是个函数赋值,还是个普通的对象赋值?
3、如何用这个对象来调用原来的函数?
假如把这几个问题解决了,委托也就明白了一半。
先看问题1,假如能够给一个对象赋函数值,如何来区别不同的函数?
首先应该明白的是:C#里是能够对一个对象赋函数值的。解决这个问题的办法是先对该对象申明,申明他能够被什么样的函数来赋值,而这个对象申明在C#里的学名就是委托。
(在C++里称为函数指针申明,相应的对象也就叫做函数指针。Java里也不同的叫法,可惜我不知道。)
而他的语法就是:
delegate [function declare];
这里的function declare就包括了:
1、函数返回类型,
2、可用来存放函数的对象名(也就是委托名)
3、函数参数
所以完整的定义能够是:
delegate int MyDelegate(object I_object);
当然,合法的委托定义能够是:
delegate void MyDelegate();
delegate void MyDelegate(object I_1,object I_2);
…
现在,上面的语法就定义了一个抽象的对象MyDelegate, 注意,这里说的是抽象的对象,也就是说,您不能直接给MyDelegate赋函数,而只能在他的实例上函数,这是C#里特别的需要。他的语法是:
MyDelegate m_delegate = new MyDelegate(和MyDelegate申明一致的函数名);
例如,以下是个完全的,合法的委托申明和实例化一个对象:
delegate int MyDelegate(object i_object);
//
MyDelegate m_delegate = new MyDelegate(MyWrite);
//MyWrite函数如下,他是满足委托的申明的。
static private int MyWrite(object i_string)
{
Console.Write(i_string);
return i_string.ToString().Length;
}
现在我们就很好的解决了第一个问题,如何定义一个对象,使该对象能够把函数当变量来赋给他。而且,能够区别不同的函数类型,主要是通过函数返回值和函数参数来共区别一类函数。
OK,第二个问题:假如有了这样的一个对象后,如何来给他赋一个函数值呢?
其实上面的实例化一个委托对象时,就已给他赋值了。上面的代码中,m_delegate就已被赋值MyWrite,因此他已具备了MyWrite函数的功能。
更有其实他的方法来给他赋值吗?有,在委托的一个应用中,能够看到其他的赋值方法。也就是另一个不好理解的概念:事件!后面会提到。
我们再来看一下最后一个问题:如何通过一个已赋值好了的委托对象,还调用他上面赋值了的函数。
这个最简单了,当一个委托实例赋了函数对象在上面后,就能够像调用原函数相同的来调用他了。因此,下面是个会法的调用:基于上面的申明。
m_delegate(“This is a delegate object to call the raw function.”);
他就等同于:
MyWrite(“This is a delegate object to call the raw function.”);
因此,上面的调用和原函数调用相同,会返回一个int结果。
OK,最后看一个完整的例子:
using System;
namespace ConsoleApplication1
{
class Class1
{
//先申明一个委托对象。
delegate int MyDelegate(object i_object);
[STAThread]
static void Main(string[] args)
{
MyDelegate m_delegate = new MyDelegate(MyWrite);
m_delegate("This is a delegate object to call the raw function.");
}
//该函数是满足上面委托对象的申明的。
static private int MyWrite(object i_string)
{
Console.Write(i_string);
return i_string.ToString().Length;
}
}
}
再来讨论一下他的应用:事件!
事件是其于委托的。我们还是先来看最开始的那个例子:
object m_obj = m_isRight?MyWrite("true"):MyWrite("false");
我想把一个函数对象赋值到m_obj上!但上面的委托只能在实例化对象的时候就直接给他赋值了。而现在是,在运行时对一个委托赋函数值。能够做到吗?
同样是有这样的向个问题,当然,前提是我们已知道有一种对象叫委托,他的实例能够赋函数对象。
下面的问题是:
1、假如能够在运行时给某个“特别委托”赋函数对象,如何实现?
标签:
版权申明:本站文章部分自网络,如有侵权,请联系:west999com@outlook.com
特别注意:本站所有转载文章言论不代表本站观点,本站所提供的摄影照片,插画,设计作品,如需使用,请与原作者联系,版权归原作者所有
IDC资讯: 主机资讯 注册资讯 托管资讯 vps资讯 网站建设
网站运营: 建站经验 策划盈利 搜索优化 网站推广 免费资源
网络编程: Asp.Net编程 Asp编程 Php编程 Xml编程 Access Mssql Mysql 其它
服务器技术: Web服务器 Ftp服务器 Mail服务器 Dns服务器 安全防护
软件技巧: 其它软件 Word Excel Powerpoint Ghost Vista QQ空间 QQ FlashGet 迅雷
网页制作: FrontPages Dreamweaver Javascript css photoshop fireworks Flash