繁体   English   中英

如何使用委托和事件?

[英]How to use delegate and event?

我正在尝试学习C#和编程,我遇到了一个问题。 我试图寻找答案却失败了,所以如果我复制另一个话题,我很抱歉。

我在窗体上有1个窗口窗体(Form1),外部类(Class1),按钮和标签。 这个类是一个简单的文件粉碎器,它从按钮点击开始。 Label1.text应该从外部类更新,显示正在切碎的文件。

我发现,我需要使用委托和事件来使这种情况正确发生,但我不知道如何正确使用它们。 代码在这里:

//Form1 
  private async void button2_Click(object sender, EventArgs e)
  {
  var task = new Task(() =>
  {
  check = true;
  bool success = FileUtilities.Shred(textBox1.Text);
  });
  task.Start();
  public void ChangeName(string text)
  {
  label3.Text = text; 
  }

  //Class1
  public static bool ShredFile(string filePath, bool shouldDelete = true)
  { 
  bool success = true; 
  try
  { 
  FileStream fs = new FileStream(filePath, FileMode.Open, FileAccess.Write);
  //Label1.text = filePath; - should be like that.

我曾尝试使用public void ChangeName来访问该属性,但它不起作用。 我无法理解我应该在哪里创建委托,事件以及订阅此事件的位置。

更新:我发现了什么问题。 我的程序中有几个线程,我无法通过课程访问表单上的标签。 我不得不使用回调,之后订阅和事件工作完美。 谢谢你, Thorsten Dittmar ,以正确的方式展示。

实际上有几种方法可以达到你想要的效果。 我会采用以下方式,因为它最容易实现,并且不涉及任何回调;-)

这背后的基本要点是:将UI更新保留给维护UI的类。 其他一切都是工具,甚至不需要知道是否有用户界面。

如果您的UI代码中有一个点,其中触发了碎化文件,请执行以下三个步骤:

  1. 更新UI,例如显示正在粉碎的文件的文件名(UI类)
  2. 撕碎文件(工具类)
  3. 显示碎化操作的成功或失败(UI类)

看到? 没有事件:-)

但你的问题是如何实际创建和使用事件,所以....

通常,事件由发送方组成,包括两部分:

  • 一个event
  • 提出事件的方法

例如,你声明它们都是这样的。

public class EventSender
{
    public event EventHandler<EventArgsType> MyEvent;

    protected void OnMyEvent(...)
    {
        if (MyEvent != null)
            MyEvent(this, new EventArgsType(...));
    }
}

EventArgsType是的子类EventArgs ,您可以使用从发送端到接收端传递信息。 一个例子:

public class EventSender
{
    public class EventArgsType : EventArgs
    {
        public EventArgsType(string fileName) : base()
        {
            FileName = fileName;
        }

        public string FileName
        {
            get;
            private set;
        }
    }

    public event EventHandler<EventArgsType> MyEvent;

    protected void OnMyEvent(string filename)
    {
        if (MyEvent != null)
            MyEvent(this, new EventArgsType(filename));
    }
}

每当事件应该提高,这是不够调用OnMyEvent 从内方法EventSender类。

现在接收器需要将自己附加到事件,然后每当触发事件时都会调用一个方法。

public class Receiver
{
    private EventSender _sender;

    public Receiver()
    {
        _sender = new EventSender();
        _sender.MyEvent += HandleMyEvent;
    }

    private void HandleMyEvent(object sender, EventSender.EventArgsType e)
    {
        // Do something with e.FileName
    }
}

那么在你的情况下我会怎么做? 我将创建一个非静态FileShredder ,它实现一个或多个类似于示例的事件,并具有一个非静态方法来粉碎文件。

在UI中启动任何任务之前,我将创建此类的实例,附加所需的事件处理程序,然后我将使用该实例来粉碎文件。 在UI类的事件处理程序中,更改标签和内容。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM