Lecture thumbnail 0:00 / 0:00 All right.

So let’s begin our discussion of the whole business of the prototype pattern and object copying by building

a very small scenario.

Now, I’m going to be building other scenarios in later sessions, but let’s suppose that we have a

class trying to get a class in here, class called person, and this person is going to have an address

and let’s say a bunch of names.

So I’m going to have a string array of names like so I’m going to keep using public fields since it’s

easier to understand and I’m going to have an address.

So we’ll have address, address like so.

And that’s going to be a new type that I will create.

So that’s going to be another class.

Let’s make it public.

Doesn’t really matter though.

Okay.

So address itself is going to be composed of two things.

There’s going to be a street name and there’s going to be a house number.

House number.

There we go.

So both of these are going to be public since we’re using public fields and I’m going to generate a

bunch of constructors and other things so that we can print these objects to the console.

So let’s do Ctrl F here to make the constructor.

Let’s do the same here, Ctrl F like so, and then I’m going to generate the formatting member.

So I will generate two string, just outputting the street name and the house number here.

And for the person, the two string is going to be a bit trickier.

So I’m going to generate the formatting members, but then I will take the array of names and I will

do string dot, join in it, join it with a space.

There we go.

So that’s going to take all the names and join them with a space.

Okay, so we’re now ready to start working with these objects.

So for example, we can make an object of type person.

All right, so let’s go var John equals new person and then I have to specify the name.

So that’s going to be a new array with John and Smith, for example.

And then the second argument is the address.

So I’ll make a new address which will specify the road as well as the house number 123 So this is a

person that we can print, so I can write line.

John, and that should hopefully give us decent output to work with as we continue exploring this example.

So here is the output.

The names are John and Smith and the address is empty.

Well, the actually it’s not empty.

We have specified the address.

So the street name is London Road and the house number is 123.

I was just confused by the lack of info here, but that’s the nesting for you.

Okay, so we have this setup.

Now let’s suppose that we also have somebody else maybe living at this address.

Maybe we just want to copy John and change a particular part of it.

So let’s take a look at the obvious stuff that will not work.

Like, for example, let’s suppose you want to make Jane So you say Var Jane equals John and you think

that by changing Jane you will make a new person.

So for example, you say Jane dot names at zero equals Jane, and then you try to print Jane.

Now this is doomed to failure for obvious reasons, because all you’ve done is you’ve copied the reference.

So now you’ve modified that same reference and you’re getting Jane in both of these locations.

So this is obviously not the correct way to go.

You have to you have to do better than that.

And the question is, well, how do we copy objects generally?

I mean, is there like a common interface for us to specify this process of copying?

And in actual fact, there might have been an interface at some point and that interface is called I

Clonable.

So the idea is that the dot net framework has this interface called I Clonable and we can try using

it.

I Clonable There we go.

Now if you go ahead and you sort of study the documentation for Clonable, then it says supports cloning,

which creates a new instance of a class with the same value as an existing instance.

Now the problem with cloning things is you never know whether it’s deep cloning or shallow cloning.

And by deep cloning, we mean copying all the inset fields recursively or just copying their references.

Like, for example, when you copy an address, do you copy the addresses inside or do you just copy

the reference?

This is one of the things that is not specified in the Clonable interface.

So for example, you might go ahead and implement the Clonable interface.

There’s actually just a single method called clone.

And notice it returns an object which is very inconvenient because I think I Clonable came in before

we even had generics.

So what you have to do is you have to make a copy of in this case person and we don’t know how.

We don’t know how this is meant to be done.

Is it meant to be a shallow copy?

And by shallow copy, we mean simply.

Returning a new person that takes the copy of the names and the address like so.

So I put names and address like so now, obviously, if I do this, then we’re not really fixing the

problem.

If I implement this kind of copying, then what happens is if I say Var Jane equals John dot clone like

so, and I say, Jane Dot.

Well let’s try changing Jane’s address for example.

Of course, here is the problem with typing.

Notice that Jane is now an object and not really a person, so you would have to at least cast it to

a person.

And then you can say, Jane, dot, address dot house number.

Maybe she has a different house number.

So let’s put three, two, one in here and we execute this.

And now both of them are three, two, one.

And this shouldn’t surprise you because we made a shallow copy when we copied the address.

We basically simply copied the reference.

So there is no specification that says I clonable is the copy.

And as a result, I mean, sure, you can take it as this approach.

You can actually force a deep copy here and I can do this, I can totally do this.

I can put an I clonable in here, I can implement the missing members here.

I can return a new address and I can copy the street name.

Remember, strings are immutable, so we’re fine here.

I can copy the house number as well.

And that would that would actually work.

So if I put it like this, then coming back here, I would say address dot clone.

Then as soon as I cast it to the appropriate type, everything should be fine.

We have three, two, one here and we have one, two, three here.

So it looks like I’ve fixed things somewhat, but still, this.

This approach is dangerous.

It’s not convenient because you’re returning object and it’s really not well specified in actual fact.

Here is a small demo of what what’s going on?

Like if you take names, which is an array and you say names dot clone, for example, you can clearly

see the documentation saying that we’re making a shallow copy of the array.

So if array is doing shallow copying on its clone, why shouldn’t we do anything other than shallow

copying?

And this kind of tells you that if you want to implement deep copying, which is what’s actually required

for the prototype pattern, then I clonable is not the interface that you should be using.

Play Stop Play Play Play Play Start Play information alert