3

I have seen on another post this and its confusing me...

public class MyClass : INotifyPropertyChanged
{
   public event PropertyChangedEventHandler PropertyChanged;  

   protected void NotifyPropertyChanged(String info)
   {
        if (PropertyChanged != null)
        {
            PropertyChanged(this, new PropertyChangedEventArgs(info));
        }
   }  

   public string MyProperty
   {
       set
       {
           if (_myProperty != value)
           {
               _myProperty = value;
               NotifyPropertyChanged("MyProperty");
           }
       }
   }
}

MyClass myClass = new MyClass();

myClass.PropertyChanged += delegate(object sender, PropertyChangedEventArgs e)
{
     actual = e.PropertyName;
};

I'm wondering about the last few lines are doing to be honest, why would the user be assiging a delegate to an event? Would't they assign a method to it (as an event handler) or even an anonymous method as the event handler?

I thought that events were meant to encapsulate delegates.....?

H H
  • 263,252
  • 30
  • 330
  • 514
Exitos
  • 29,230
  • 38
  • 123
  • 178

6 Answers6

4

You always subscribe to an event (or unsubscribe from it) using a delegate. Even if you do:

button.Click += HandleButtonClick;

that's equivalent to

button.Click += new EventHandler(HandleButtonClick);

When you say:

Would't they assign a method to it (as an event handler) or even an anonymous method as the event handler?

That's exactly what the last few lines of code do. That's what delegate (...) { ... } is.

I thought that events were meant to encapsulate delegates.....?

Events provide an implementation of the observer pattern, using delegates as the observers.

Jon Skeet
  • 1,421,763
  • 867
  • 9,128
  • 9,194
  • Shouldn't "You always subscribe to an event (or unsubscribe from it) using an event" read "[...] using a *delegate*"? – Ani Jan 19 '12 at 16:01
  • Jon, that's interesting what your saying about the observer design pattern are you saying that events were created to address this design pattern? – Exitos Jan 23 '12 at 10:50
1

Description

This class implements the INotifyPropertyChanged interface

MSDN Notifies clients that a property value has changed.

The INotifyPropertyChanged interface is used to notify clients, typically binding clients, that a property value has changed.

This is used for example on controls like the Datagrid. It signals the control that the property has changed and the control should rerender.

About the Event

You always subscribe to an event.

MyClass myClass = new MyClass();
myClass.PropertyChanged += delegate(object sender, PropertyChangedEventArgs e)
{
     actual = e.PropertyName;
};

is doing the same as

MyClass myClass = new MyClass();
myClass.PropertyChanged += new PropertyChangedEventHandler(myClass_PropertyChanged);

void myClass_PropertyChanged(object sender, PropertyChangedEventArgs e)
{
     actual = e.PropertyName;     
}

or

MyClass myClass = new MyClass();
myClass.PropertyChanged += myClass_PropertyChanged;

void myClass_PropertyChanged(object sender, PropertyChangedEventArgs e)
{
     actual = e.PropertyName;    
}

More Information

Community
  • 1
  • 1
dknaack
  • 60,192
  • 27
  • 155
  • 202
1

The += adds an anonymous delegate to the event. Instead of creating a named method with the signature object sender, PropertyChangedEventArgs e, you can use C#2.0 syntax to create such delegates anonymously in the body of another function. Another way of doing it would be to use a more concise lambda syntax from C#3.5+:

myClass.PropertyChanged += (sender, e) { actual = e.PropertyName; };
Sergey Kalinichenko
  • 714,442
  • 84
  • 1,110
  • 1,523
1

This syntax was introduced in C# 2.0 They are using an anonymous method here, rather than having to create an actual instance method of the class. It's generally considered cleaner.

In C# 3 and above, a Lambda expression could have been used as well.

Erix
  • 7,059
  • 2
  • 35
  • 61
  • An edit to include the lambda notation for the delegate would be useful, I think... – Tetsujin no Oni Jan 19 '12 at 15:01
  • myClass.PropertyChanged += (x,y) => actual = y.PropertyName; – Jimmy W Jan 19 '12 at 15:06
  • okay this makes sense, I think perhaps the syntax of an anonymous method http://msdn.microsoft.com/en-us/library/0yw3tz5k%28v=vs.80%29.aspx makes it confusing since it contains the word delegate. And somebody said to me that you could have an anonymous method. I guess what they mean is a delegate with an anonymous method. – Exitos Jan 19 '12 at 15:56
  • @Exitos: I don't see why it makes it confusing - it's creating an instance of a delegate type. – Jon Skeet Jan 23 '12 at 10:51
1

They are not assigning a delegate to an event, they are adding a subscriber to that event using an anonymous method.

Also, as an aside, the NotifyPropertyChanged method should be changed to:

protected void NotifyPropertyChanged(String info)
{
    PropertyChangedEventHandler handler = PropertyChanged;
    if (handler != null)
    {
        handler(this, new PropertyChangedEventArgs(info));
    }
}

Since there is a potential race condition between the null check and invocation of the delegate.

Rich O'Kelly
  • 41,274
  • 9
  • 83
  • 114
1

Technically, you are correct; events encapsulate delegates. However, event handlers themselves are delegates.

Jimmy W
  • 539
  • 3
  • 11