C#中为什么要使用委托的?

来源:互联网 发布:淘宝下拉选93es.com 编辑:程序博客网 时间:2024/06/01 10:19

C#中为什么要使用委托的?
相信经过上面的介绍,大家应该对委托不再陌生了吧,然而我们为什么需要委托的,好好地为什么要实例化中间这个对象的,为什么不直接在MyMethod方法里面调用InstanceMethod方法的,这样不是自找麻烦的吗?为了大家可以更好的明白为什么要使用委托,下面通过一个Window Form的 ”文字抄写员“ 程序要解释下为什么。

程序实现的功能是:在下方文本框输入文字,勾选“书写到”组合框中的“文本区1”或“文本区2”复选框后点击“开始”按钮,程序会自动将文本框中的文字”抄写“到对应的文本区中去。程序界面如下:
这里写图片描述
传统的实现代码为:
复制代码

namespace 文字抄写员{    public partial class Form1 : Form    {        public Form1()        {            InitializeComponent();        }        private void button1_Click(object sender, EventArgs e)        {            if (checkBox1.Checked == true)            {                textBox1.Clear();                textBox1.Refresh();                // 调用方法WriteRichTextBox1想文本区1写入文字                this.WriteTextBox1();                textBox3.Focus();                textBox3.SelectAll();            }            if (checkBox2.Checked == true)            {                textBox2.Clear();                textBox2.Refresh();                // 调用方法WriteRichTextBox2想文本区2写入文字                this.WriteTextBox2();                textBox3.Focus();                textBox3.SelectAll();            }        }        private void WriteTextBox1()        {            string data = textBox3.Text;            for (int i = 0; i < data.Length; i++)            {                textBox1.AppendText(data[i].ToString());                //间歇延时                DateTime now = DateTime.Now;                while(now.AddSeconds(1)>DateTime.Now)                { }            }        }        private void WriteTextBox2()        {            string data = textBox3.Text;            for (int i = 0; i < data.Length; i++)            {                textBox2.AppendText(data[i].ToString());                //间歇延时                DateTime now = DateTime.Now;                while (now.AddSeconds(1) > DateTime.Now)                {  }            }        }    }}

复制代码

然而我们从代码中会发现WriteTextBox1()方法和WriteTextBox2()只有一行代码不一样的( textBox1.AppendText(data[i].ToString()); 和 textBox2.AppendText(data[i].ToString());),其他都完全一样,而这条语句的差别就在于向其中写入文本的控件对象不一样,一个是TextBox1和TextBox2,现在这样代码是实现了功能,带式我们试想下,如果要实现一个写入的文本框不止2个,而是好几十个甚至更多,那么不久要写出同样多数量的用于写入文本区的方法了吗?这样就不得不写重复的代码,导致代码的可读性就差,这样写代码也就是面向过程的一个编程方式,因为函数是对操作过程的一个封装,要解决这个问题,自然我们就想到面向对象 编程,此时我们就会想到把变化的部分封装起来,然后再把封装的对象作为一个对象传递给方法的参数的(这个思想也是一种设计模式——策略模式,关于设计模式系列会在后面也会给出的),下面就利用委托来重新实现下这个程序:
复制代码

namespace 文字抄写员{    public partial class Form1 : Form    {        // 定义委托        private delegate void WriteTextBox(char ch);        // 声明委托        private WriteTextBox writeTextBox;        public Form1()        {            InitializeComponent();        }        private void button1_Click(object sender, EventArgs e)        {            if (checkBox1.Checked == true)            {                textBox1.Clear();                textBox1.Refresh();                // 实例化委托                writeTextBox = new WriteTextBox(WriteTextBox1);                // 作为参数                WriteText(writeTextBox);                textBox3.Focus();                textBox3.SelectAll();            }            if (checkBox2.Checked == true)            {                textBox2.Clear();                textBox2.Refresh();                // 实例化委托                writeTextBox = new WriteTextBox(WriteTextBox2);                // 作为参数                WriteText(writeTextBox);                textBox3.Focus();                textBox3.SelectAll();            }        }        private void WriteText(WriteTextBox writetextbox)        {            string data = textBox3.Text;            for (int i = 0; i < data.Length; i++)            {                // 使用委托                writetextbox(data[i]);                DateTime now = DateTime.Now;                while (now.AddSeconds(1) > DateTime.Now)                { }            }        }        private void WriteTextBox1(char ch)        {            textBox1.AppendText(ch.ToString());        }        private void WriteTextBox2(char ch)        {            textBox2.AppendText(ch.ToString());        }    }}

复制代码

引入委托后实现的代码中,我们通过WriteText方法来向文本区写入内容,它所执行的只是抽象的”写文本“操作,至于究竟像那个文本框写入文字,对于编写WriteText方法的程序来说是不知道,委托writeTextBox就像一个接口一样(面向对象设计原则中有一个很重要的原则就是——针对接口编程,不针对实现编程),屏蔽了操作对象的差别(方法到底是想向文本区1写入文本还是像文本区2写入文本,现在我方法里面不需要去关心,我只需要集中在实现”书写文本”这个操作,而不必纠结操作对象的选择)。

三、委托的作用到底是什么?——委托总结陈词

相信通过上面两部分大家也明白了委托是个什么东西以及C#中为什么要引入委托这个概念。现在就总结下引入委托后到底作用在那里的? 从上面的委托代码中可以发现,引入委托后,编程人员可以把方法的引用封装在委托对象中(把过程的调用转化为对象的调用,充分体现了委托加强了面向对象编程的思想。),然后把委托对象传递给需要引用方法的代码,这样在编译的过程中我们并不知道调用了哪个方法,这样一来,C#引入委托机制后,使得方法声明和方法实现的分离,充分体现了面向对象的编程思想。

委托对自己的总结:

我是一个特殊的类,我定义了方法的类型,(就像int定义了数字类型一样,当用一个方法实例化委托对象时,这个委托就代表一个方法,这个方法的类型就是委托类型),我可以将方法当做另一个方法的参数来进行传递,使得程序更容易扩展

四、小结

写到这里本专题介绍的内容也结束了,在本专题中有些地方提到了一些设计模式的知识的,如果有朋友对设计模式还没有开始学习的话,建议大家都去学习下的,并且我也会在后面的系列中向大家分享下我的理解的。对于本系列的下一专题将和大家分享下我理解的事件到底是个什么样的概念。最后希望本专题可以让大家进一步理解委托。

0 0