1个发布者类事件,多个订阅者,不同参数

时间:2017-10-09 14:19:38

标签: c# events delegates eventargs

我正在使用委托和事件在我的应用程序中传递数据,但希望触发1事件将不同的数据集传递到不同的地方。

问题

我有一个主要的课程,可以完成一些工作。一旦工作完成,我希望它通知许多其他类(包括UI),以便可以执行其他操作。其他课程所需的信息不同。

示例

Main.cs - 执行操作并想要更新UI,发送文本消息并写入日志文件。

UI更新DataGrid,因此需要各个字段。

日志文件writer需要将整行作为数组/ List。

文本消息代码需要Line,LineNumber和FileName,但需要用制表符分隔字符串。

当我只是尝试更新UI时,以下所有内容都能正常工作,但当我尝试将不同的信息发送到不同的地方时,我会遇到错误。

我尝试过创建EventArgs的不同扩展,但是如果我尝试使用不同的签名声明2个委托,那么我会收到一条错误消息。

非常感谢任何帮助。

FrmMain.cs

Main main = new Main();
main.PatternFound += OnPatternFound;

main.DoSomeWork();

private void OnPatternFound(object source, LineEventArgs e)
    {
        UpdateDataGrid(e.Line, e.FileName, e.LineNumber);
    }

private void UpdateDataGrid(string line, string file, int lineNumber)
    {
        if (InvokeRequired)
        {
            Invoke(new Action<string, string, int>(UpdateDataGrid), line, file, lineNumber);
        }
        else
        {
            dgResults.Rows.Add(line, file, lineNumber);
        }            
    }

Main.cs

public delegate void PatternFoundEventHandler(object sender, LineEventArgs e);
public event PatternFoundEventHandler PatternFound;

protected virtual void OnPatternFound(string line, string fileName, int lineNumber)
    {
        PatternFound?.Invoke(this, new LineEventArgs { Line = line, FileName = fileName, LineNumber = lineNumber });
    }

public void DoSomeWork()
{
    //Finished my work
    OnPatternFound(line, file, lineNumber);
}

LineEventArgs.cs

public class LineEventArgs : EventArgs
{
    public string Line { get; set; }
    public string FileName { get; set; }
    public int LineNumber { get; set; }
}

1 个答案:

答案 0 :(得分:1)

由于多种原因,您尝试实现的目标可能不是一个好方法。你决定坚持参加事件,这意味着你决定做所谓的&#34;控制倒置&#34;。

你以这样的方式实现了你的主类:&#34;我正在进行某种模式匹配,我将告诉谁对我发现的东西感兴趣,我正在以我的event-args实现定义的方式进行&#34;因此,现在由订阅者按原样获取或保留此信息。

严格地说,你说的话......

  

执行操作并想要更新UI,发送文本消息并写入日志文件。

...不是你实现的,因为主类没有做到这一点。无论如何,在我看来,保持事件驱动是一个可行的解决方案,但是你需要更改你的上游代码。

例如,您可以将三个不同的事件处理程序附加到此单个事件。然后,每个处理程序都必须以所需的格式转换数据:日志记录处理程序必须将其转换为数组,UI处理程序必须连接它,依此类推。

另一种选择是您有一个处理程序并分配给三种不同的方法,例如OnPatternFound方法会调用UpdateUI方法和Log方法等等。< / p>

最后你还可以摆脱控制反转并将你的逻辑移到主类,但我会不推荐它!你的方法很好,但你不应该尝试以三种不同的方式调用同一个事件。这取决于订阅者。