Annotating `this` in Functions and Objects
Fixing this
with the function
Keyword
The first thing we need to do is add a type annotation for this
inside the add
function:
function add(this: { x: number; y: number }) { return this.x + this.y;}
Note that we've used this
as the name of the parameter, but it
Transcript
00:00 Okay, the first thing we need to do is within this add function, we need to type this, implicitly has an any because it does not have a type annotation. Turns out you can provide a type annotation for this within the add function. So you can say this, just like this, you can
00:17 say X number and Y number. And so by using the name this inside this add function, it actually types the this that it belongs to. So this doesn't count as a parameter that you need to add to the function. You can see the hit down here, calculator.add, don't need
00:34 to pass in any numbers. It's just using the context of this to get it working. But what about this error? Object is possibly undefined. What on earth could that error mean? And why actually, is this whole thing breaking down the bottom? Why isn't this working? Let me
00:50 just actually run the correct one because I'm on the solution now. So this is still breaking. Great, great, great. Why is it breaking? Well, it's because we cannot use an arrow function as a method when we do objects like this. So with classes, you can do a,
01:08 you can use an arrow function within the class and it will kind of automatically bind the this to the context of the class. Very useful. But in this setup, it just doesn't work. If we try to add this like X number and Y number to our arrow function, first of all, it will say an arrow function cannot have a this parameter. So it's just not letting us do it. The only
01:27 way to get this working actually is to change it to a normal function declaration. And now as a normal function declaration, it has access to the this in which it's being called, which an arrow function kind of doesn't. And it means that our tests just pass here. The other
01:44 way, of course, that we could do this is just to declare this stuff in line. It's just to have, we take the add there and we put it kind of like a method on this add there. So we remove the this. And in fact, you don't need to type it anymore. So I'll just remove,
01:59 clean that up a little bit. And it has access to this dot X and this dot Y automatically. And the same with set values too. We can just like grab all of this stuff, stick them in there and set values like bam, it's just working. So again, no need to type the this here. And
02:15 you notice, by the way, too, that when we have this, this as part of the parameters of set values, you don't need to pass it as an argument to set values down there. Very cool. So that's how we basically handled this. And you notice that this just looks very similar to a class. And often what you'll see, this is kind of how classes run under the hood
02:35 too. So this calculator has add, has set values, all working beautifully. And you can, if you ever need to declare like functions outside of these kind of like object-y classes, then you can use the this parameter to make sure they're strongly typed to the context in which they're called.