多播委托:在其他方法中添加对委托的方法引用时的不同行为

本文关键字:方法 引用 添加 其他 多播 | 更新日期: 2023-09-27 18:25:28

我有下面的代码,它声明了一个委托:

delegate void EmployeeSalaryCalculated(int idEmp);

我有这些简单的类:

    class Employee
    {
        public void CalculateSalary(int idEmp){}
    }
    class Payroll
    {
        public void EmpSalNotification(int idEmp) { }            
        public void SetMethod(ref EmployeeSalaryCalculated esc)
        {
            esc += this.EmpSalNotification;
        }         
    }
    class HR
    {
        public void EmpSalNotification(int idEmp) { }           
        public void SetMethod(ref EmployeeSalaryCalculated esc)
        {
            esc = this.EmpSalNotification;
        }
    }

下面的按钮处理程序使用了上面的类:

private void btnStart_Click(object sender, EventArgs e)
        {              
            Payroll payroll = new Payroll();
            HR hr = new HR();            
            EmployeeSalaryCalculated empSalCalculated = null;
            empSalCalculated += payroll.EmpSalNotification;
            empSalCalculated += hr.EmpSalNotification;
            // This invokes both methods - fine. 
            // empSalCalculated.GetInvocationList() returns 2
            empSalCalculated.Invoke(108);
            EmployeeSalaryCalculated empSalCalculated2 = null;
            payroll.SetMethod(ref empSalCalculated2);
            hr.SetMethod(ref empSalCalculated2);
            // This however, invokes only one method!
            // empSalCalculated2.GetInvocationList() returns 1
            empSalCalculated2.Invoke(108);    
        }

尽管通过ref传递了委托对象empSalCalculated2,但它只执行一个函数,而委托对象empSalCalculated执行两个函数。

有什么想法吗?

多播委托:在其他方法中添加对委托的方法引用时的不同行为

问题出现在HR.SetMethod类的这一行:

esc = this.EmpSalNotification;

这一行覆盖esc以前的任何值。因此,给定从对象调用SetMethod的顺序,empSalCalculated2只包含执行的HR实例中的方法。

要更正此问题,您可能需要重写HR.SetMethod:

esc += this.EmpSalNotification;

或者颠倒SetMethod的调用顺序:

hr.SetMethod(ref empSalCalculated2);
payroll.SetMethod(ref empSalCalculated2);

我认为这是您的人力资源类中的一个拼写错误

class HR
    {
        public void EmpSalNotification(int idEmp) { }           
        public void SetMethod(ref EmployeeSalaryCalculated esc)
        {
            // this is =, not +=, so only one ref is held at a time
            esc = this.EmpSalNotification; 
        }
    }

只是代码中的一个拼写错误:

esc += this.EmpSalNotification;  

 esc = this.EmpSalNotification;