Lecture thumbnail 0:00 / 0:00 So the use of the event keyword is one way in which you can implement the observer pattern.

But it’s not the only way, because there are other mechanisms which are available for you to implement

your own observers.

Now, as you probably have heard, there is something called reactive extensions, also abbreviated

as RCS.

And even though we’re not going to specifically take a look at reactive extensions in this course,

we do need to care about some of the interfaces which are were introduced by reactive extensions but

are now available as part of the.

Net framework generally.

And those interfaces are I observer and I observable.

So in theory what you could do is you could build the observer design pattern using these two interfaces.

And in this lecture we’re going to take a look at exactly how you can do that to get functionality which

is similar to what you get with ordinary events, but at the same time different because you get certain

benefits.

So one of the downsides of ordinary events is this idea of event leaks.

Basically the idea that once you have an event subscription, it kind of becomes invisible in the sense

that you don’t see the actual subscription anywhere.

Well, with the eye observer and eye observable interfaces, all of a sudden the subscription does in

fact become visible.

And furthermore, what you typically see is that your subscription as a separate object will also implement

the Idisposable interface so that when you don’t need the subscription anymore, you can just take the

object and you can dispose it.

And that kind of breaks the connection between the subscriber and the object that’s being observed.

So let’s try putting all of this together and implementing a very simple event subscription model using

those two interfaces.

Now, first of all, what I’m going to do is I’m going to introduce a class for describing some sort

of an event, something that happens to a system and we can inherit from this class.

So, for example, let’s suppose we want to be notified of situations when a person falls ill so we

can make a false ill event which is going to inherit from event.

And here inside this event, we can keep any sort of information about this event, like the kind of

information that you would need when somebody falls ill.

Maybe you want to call a doctor to their address.

So you need that address.

I’m going to have just a public field here called address.

Obviously, you can make these classes a lot more sophisticated, but we’re just going to keep it simple

for now.

So let’s imagine that we have a person class and a person can fall ill, and when they fall ill, we

should be able to do something like, let’s say, call a doctor, for example.

But we want to basically raise an event just as we would with ordinary net events.

But we want to do this using this functionality of I observer and I observable.

So the question is how can we actually set all of this up?

Well, the first thing we’ll do is we’ll implement the I observable interface specifying that this object

is observable.

And when you observe it, it generates an event.

So notice we’re using the base event class here.

We’re not saying false ill event because theoretically a person can also generate all sorts of other

events, like maybe it’s a person’s birthday and so they generate a birthday event.

So we have a general kind of event and then we implement the member.

There’s only one member called Subscribe here and you’ll notice straight out of the box that this member

implements Idisposable.

So the idea here is that this idisposable represents the subscription itself so that when you call dispose,

you break the connection, you break the subscription.

And so there is no problem of leaking events because essentially they are disposable now.

Okay, So with this setup, what we need to be able to do is we need to hold on to the subscriptions.

We need to have a set of subscriptions because you can have several different objects which subscribe

to the events that happen to this particular person.

But we haven’t described what a subscription actually is.

A subscription is obviously a disposable class of some kind, but what does it look like?

Let’s actually implement this now here I’m going to implement this as a private class because we’re

never going to expose this class itself.

We’re only going to expose it as an idisposable interface.

So we’re going to have a class called subscription, which is going to be disposable like so.

So we need to implement the disposable interface like so.

And what are we going to describe in the subscription?

Well, we need two things.

We first of all, need to know which object this subscription is subscribing to.

And the second thing is who is actually doing the subscribing?

So let’s make a constructor.

So we’ll make a constructor.

The first argument is the object that we.

Are subscribing to.

So in this case, it’s a person since this is what we are actually monitoring for events.

But the other object is more interesting because it’s not just some object or dynamic or whatever.

Instead, we use the other interface of the observer observable duality.

So we use an interface called I Observer.

So an I observer also uses a generic argument for an event, and it’s basically any component which

is able to receive events of this particular type.

So we’ll call this observer.

So the idea of a subscription is very simple.

We simply store both of these so we store the person.

So this can be a private read only field.

We store the observer itself, but we might want to keep the observer public as opposed to private.

So here I will first of all introduce this field, but I will actually go here and I will make it public.

Use the capital O here like so, and then just make the change right here.

Okay.

So this is the initialization.

You’ll notice there are no actual behaviors.

It’s just a data storage mechanism for connecting the observable and the observer.

You could generalize it even more.

You could put an I observable here instead of person, but it doesn’t really matter for our demo.

Now let’s before we implement dispose, because that’s going to be the really interesting part.

Let’s actually go back into person and let’s give person some sort of way of storing all of these subscriptions.

Because now that we have a subscription class, we can make several subscriptions.

So here I will have a private read only field of type hashset of subscription.

So I need to import this, let’s call it subscriptions.

And here I’ll just initialize it with the default hashset initialization.

So that’s, that’s all there is to it.

And now what we can do is we can finally implement the subscribe method and actually get the observer

to subscribe to the events that happen on the observable.

So what we do is we construct a subscription.

So we say var subscription equals new subscription where we specify this as the object that’s being

observed and we provide the observer which is provided as the argument right here.

Then we add it to the set of subscriptions.

So we say subscriptions dot add, so we add the subscription, but we also return it.

We also return it as an Idisposable So we return subscription.

But notice we’re not returning a subscription object.

We’re returning an Idisposable So all we’re doing is returning something which has a dispose method

that you can subsequently call.

So you can think of it like a memento of sorts because it really doesn’t expose all of its functionality,

just exposes the bare minimum that you can use to subsequently do this one thing.

So it’s kind of a quasi memento kind of implementation.

And now finally we can implement the dispose method on the subscription.

So we haven’t done that yet.

So the idea is that when you dispose of a subscription, you basically remove it from the set of subscriptions

on the observable, which in our case is person.

So here we say person dot subscriptions, dot remove, and we remove this particular subscription.

That’s pretty much all that we need to do.

Okay, so now we’ve got this interesting setup where we have an eye observer, I observable duality.

The person itself is observable.

So the question is who exactly is the observer?

Who is going to observe this?

Now, strictly speaking, what we need is we need some sort of class which implements an eye observer.

So we need some sort of class which implements an eye observer.

Of course, there are simplifications in reactive extensions, for example, so that you don’t have

to construct your own observers.

But we’re going to do this just so that you understand what’s going on.

So as you can see, eye observers also an interface.

It specifies what kind of events it’s going to get.

In this case, we have a class called event for doing that.

And then let’s actually implement all the different members.

Okay.

So as you can see, there are three different members.

There is uncompleted on error and on next.

So those are fairly self descriptive.

So on error is something that’s going to be called whenever there is an error in the event stream.

We’re not going to deal with this in this particular case, so we’re going to ignore this and similarly

we’ll ignore uncompleted.

Uncompleted is basically the method that will get called when there are no more events that can be generated.

So, for example, let’s suppose that a person is dead.

If a person is dead, then obviously they cannot fall ill.

They in fact they cannot generate any other event because they are dead.

They are not functioning anymore.

So then you would send some sort of completed signal completed event that would tell the subscribers

that no more events will be generated from that particular object.

Now, the one we care about is on next.

This is the method that’s going to be invoked when something happens, when, let’s say, a person falls

ill.

So if the person falls ill, we can take a look at this value here and we can say that if this is a

falls ill event, so if value is false ill event args, then we can take args and we can, let’s say,

call a doctor for this particular person.

So here we can say that let’s say a doctor is required at and then we specify args dot address.

So we grab the address of the person and we say that the doctor is needed for this particular address.

So this on next is what’s going to process the whole thing.

Now of course we have to make a connection between the person and our observer.

In this case, my observer is the program itself.

So let’s actually do everything in the constructor.

So I’ll make a constructor here.

And in the main method we’ll just call the constructor.

It’s a bit easier than doing it differently.

So in the constructor we make a person like so then we subscribe to an event on that person.

So we say var subscription equals person dot subscribe this.

So notice we are passing this so into the subscribe method.

We are passing an eye observer because program happens to be an eye observer and that’s exactly what

we’re passing here.

And if we come back to the interface, if we come back to the subscribe method here, you can see we’re

taking an eye observer of event.

So everything kind of fits.

Everything kind of matches.

We subscribe to this notice, this variable, this variable is an eye disposable.

We can actually be explicit about it.

We can say eye disposable.

We can even use some of the newer C-sharp syntax.

So we can say using eye disposable sub.

And this means that at the end of the constructor it’s going to dispose.

This particular subscription depends on whether this is what you want or not.

So in this particular case, let’s actually kind of try to sort of fire this thing, try to subscribe

to an event and and, you know, see whether or not it actually works.

I’ll get rid of the using for now.

It’s not relevant to our discussion.

So what I’m going to do is I’m now going to make sure that with this particular subscription, we can

actually get some sort of an event.

So we going to take person.

And now what we’re going to do is we’re going to actually generate one of those events.

So coming back to person itself, you’ll notice that at the moment we don’t really have any way of actually

firing off the event.

So we don’t have any way of actually telling people that somebody has in fact fallen ill.

So let’s actually do that.

So, um, let’s have a method called fall Ill.

Now here what you would do is you would go through every single element in the subscription.

You would find the observer for that subscription and then you would tell the Observer that, you know,

something has happened.

So for each var s in subscriptions, so we have a subscription.

And what we can do here is we can grab the observer of that subscription and we can call on next, not

on completed on next.

So we call on next and on next takes the actual event.

So here we can specify a false ill event and in the fall ill event we can also specify that the address

is equal to 123 London Road, for example.

So this is how you would actually fire the whole thing on every single member, every single subscription

effectively.

So now that you have this in place, you have this invocation in place, we can come back down here

and well, we already have the subscription here so we can get a person to fall ill so we can say person

falls ill and now we can try and.

See whether or not this actually works.

All right.

As you can see, we have triggered the event and we can see that a doctor is required at 123 London

Road.

Of course, there are plenty of simplifications that reactive extensions try to do in order to make

us sort of handle these events without having to implement your own AI observer, because this part

is particularly tedious.

And if you think about ordinary net events, when you subscribe to an event, you don’t declare the

class that subscribes to an event to conform to some sort of interface.

You just provide some sort of lambda.

And it’s certainly possible to do this using reactive extensions.

So here, instead of just having a subscription like the following, what you can do is you can get

away without any of this.

You can say something like the following, so you can say person.

Now remember, person is an AI observable, so we can have all sorts of weird link operators on it.

You can say person of type.

Okay, so this of type thing is something that requires reactive extensions, which I’m just going to

quickly, quickly add behind the scenes here.

So I’m going to.

Add system reactive.

You can’t see this, but.

But I’ll just do this quickly right here.

All right.

And now hopefully we get to we get to see some sort of imports, although of type.

Yep.

We can now use of type.

So here is a different way of subscribing.

Well, first of all, saying that we’re only interested in the Falls Ill event, we’re not interested

in other types of event because remember you have a base class event and this is what gets output.

And now I can say I’m going to take a person, I can take all the events of type falls event and for

every single one of them, I can do a subscribe like this.

I can call, subscribe and I can take the argument args and I can have some sort of information.

Like once again I can replicate what we have here.

So this whole console.writeline thing, I can just stick it right here and it’s going to perform pretty

much the same thing as it did before.

So if we do this, then of course what happens is the management of the subscription gets handled now

by the reactive extensions.

So it’s a different mechanism, but the end result is exactly the same.

Let’s actually run this just so that you can see.

Well, I actually did this in a wrong order.

I’m sorry.

This the the actual falls ill thing has to come after the subscription has been made.

So it has to be done like this.

Let’s let’s run this again.

Let’s take a look at how this actually works.

And as you can see, the end result is exactly the same.

So what is the takeaway from this entire lecture?

Well, the takeaway is that there is an alternative mechanism for observers and observables to using

net events.

And that alternative mechanism is a bit weird because on the one hand, you have these eye observable

and eye observer interfaces which are just part of the net base class library.

They’re not specific to reactive extensions, mind you.

They are generally available and you can use them in your own code and just just build your own subscription

class.

Or alternatively, what you can do is you can just leverage reactive extensions, which provides you

lots of these wonderful operators.

You have utility methods so you don’t have to implement your own eye observer, for example.

So it makes things a lot easier.

So this is an alternative mechanism.

It is particularly useful when you have streams of events, you have streams of data being generated

and you want to subscribe to those notifications and you want to process them using various Linq like

operators.

And keep in mind that reactive extensions has lots of operators which are even more sophisticated than

what you get with ordinary Linq operators.

So all of this stuff is wonderful and provide an alternative mechanism to implementing the observer

pattern.

Play Play Play Stop Play Play Play Play Start Play information alert