You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: ObjectOrientedProgramming.md
+166-2Lines changed: 166 additions & 2 deletions
Original file line number
Diff line number
Diff line change
@@ -77,10 +77,12 @@ Objects of the same type are created by calling the constructor function with th
77
77
78
78
In JavaScript, the thing called `this` is the object that "owns" the code. The value of `this`, when used in an object, is the object itself. This is because the execution context changes after an object is created. In a constructor function `this` does not have a value. It is a substitute for the new object. The value of `this` will become the new object when a new object is created.
79
79
80
-
<i>Note that this is not a variable. It is a keyword. You cannot change the value of this.</i>
80
+
<i>Note that `this` is not a variable. It is a keyword. You cannot change the value of `this`.</i>
81
81
82
82
As a rule all constructor functions should start with a capital letter to let other programmers know that you need to call this function using the `new` keyword.
83
83
84
+
To add properties to a constructor function you must prepend them with `this`.
85
+
84
86
```javascript
85
87
functionElf(name, weapon) {
86
88
this.name= name;
@@ -105,4 +107,166 @@ Peter doesn't have `attack` as it's own method but when `Peter.attack()` gets ca
105
107
106
108
This is efficient because `attack` now exists in the same location in memory and we now no longer have to copy it multiple times in order to use it.
107
109
108
-
<i>Note: Remember, we can't use arrow functions in constructors because arrow functions are lexically scoped and will point the value of `this` back to the function itself where it was written.</i>
110
+
<i>Note: Remember, we can't use arrow functions in constructors because arrow functions are lexically scoped and will point the value of `this` back to the function itself where it was written.</i>
111
+
112
+
#### Using ES6 Classes
113
+
114
+
Constructor functions inside classes get run every time we instantiate the class.
115
+
116
+
```javascript
117
+
classElf {
118
+
constructor(name, weapon) {
119
+
this.name= name;
120
+
this.weapon= weapon;
121
+
}
122
+
attack() {
123
+
return'attack with '+this.weapon
124
+
}
125
+
}
126
+
127
+
constpeter=newElf('Peter', 'stones')
128
+
peter.attack() // -> attack with stones
129
+
130
+
console.log(peter instanceof Elf) // -> true
131
+
```
132
+
133
+
<i>Note: In JavaScript ES6 classes are syntactic sugar. Under the hood they are still technically using prototypal inheritance. JavaScript classes are still technically objects.</i>
134
+
135
+
---
136
+
<br>
137
+
138
+
## More of `this`
139
+
140
+
#### Implicit Binding
141
+
142
+
```javascript
143
+
constperson= {
144
+
name:'Corey',
145
+
age:26,
146
+
hi() {
147
+
console.log('Hi '+this.name)
148
+
}
149
+
}
150
+
151
+
person.hi() // -> Hi Corey
152
+
```
153
+
154
+
#### Explicit Binding: with `call()`
155
+
156
+
We know that in order to tell what the this keyword is referencing we first have to look at where the function is being invoked. Now, this brings up the question, how can we invoke greet but have it be invoked with the `this` keyword referencing the person object. We can’t just do person.greet() like we did before because person doesn’t have a greet method. In JavaScript, every function contains a method which allows you to do exactly this and that method is named `call()`. `call()` is a method on every function that allows you to invoke the function specifying in what context the function will be invoked.
157
+
158
+
Again, `call()` is a property on every function and the first argument you pass to it will be the context (or the focal object) in which the function is invoked. In other words, the first argument you pass to call will be what the `this` keyword inside that function is referencing.
159
+
160
+
```javascript
161
+
functiongreet(lang1, lang2, lang3) {
162
+
console.log(`Hello, my name is ${this.name} and I know ${lang1}, ${lang2} & ${lang3}.`)
163
+
}
164
+
165
+
constperson= {
166
+
name:'Corey',
167
+
age:26
168
+
}
169
+
170
+
greet.call(person, 'JavaScript', 'PHP', 'Ruby')
171
+
// -> Hello, my name is Corey and I know JavaScript, PHP & Ruby.
172
+
```
173
+
174
+
#### Explicit Binding: with `apply()`
175
+
176
+
`apply()` is the exact same thing as `call()`, but instead of passing in arguments one by one, you can pass in a single array and it will spread each element in the array out for you as arguments to the function.
177
+
178
+
```javascript
179
+
functiongreet(lang1, lang2, lang3) {
180
+
console.log(`Hello, my name is ${this.name} and I know ${lang1}, ${lang2} & ${lang3}.`)
181
+
}
182
+
183
+
constperson= {
184
+
name:'Corey',
185
+
age:26
186
+
}
187
+
188
+
constlanguages= ['JavaScript', 'PHP', 'Ruby']
189
+
190
+
greet.apply(person, languages)
191
+
// -> Hello, my name is Corey and I know JavaScript, PHP & Ruby.
192
+
```
193
+
194
+
#### Explicit Binding: with `bind()`
195
+
196
+
`bind()` is the exact same as `call()` but instead of immediately invoking the function, it’ll return a new function that you can invoke at a later time. Therefore we should save it to a variable.
197
+
198
+
```javascript
199
+
functiongreet(lang1, lang2, lang3) {
200
+
console.log(`Hello, my name is ${this.name} and I know ${lang1}, ${lang2} & ${lang3}.`)
greeting() // -> Hello, my name is Corey and I know JavaScript, PHP & Ruby.
211
+
```
212
+
213
+
#### `new` Binding
214
+
215
+
The third rule for figuring out what the this keyword is referencing is called the `new` binding. Whenever you invoke a function with the `new` keyword, under the hood, the JavaScript interpreter will create a brand new object for you and call it `this`. So, naturally, if a function was called with `new`, the `this` keyword is referencing that new object that the interpreter created.
216
+
217
+
```javascript
218
+
functionPerson(name, age) {
219
+
/*
220
+
Under the hood, JavaScript creates a new object called `this`
221
+
which delegates to the Person's prototype on failed lookups. If a
222
+
function is called with the new keyword, then it's this new object
223
+
that the interpreter created that the this keyword is referencing.
224
+
*/
225
+
226
+
this.name= name
227
+
this.age= age
228
+
}
229
+
230
+
constme=newPerson('Corey', 26)
231
+
```
232
+
233
+
#### Lexical Binding
234
+
235
+
With arrow functions, `this` is determined “lexically”. Arrow functions don’t have their own `this`. Instead, just like with variable lookups, the JavaScript interpreter will look to the enclosing (parent) scope to determine what `this` is referencing.
236
+
237
+
```javascript
238
+
constperson= {
239
+
name:'Corey',
240
+
age:26,
241
+
languages: ['JavaScript', 'PHP', 'Ruby'],
242
+
243
+
greet() {
244
+
consthello=`Hello, my name is ${this.name} and I know `
person.greet() // -> Hello, my name is Corey and I know JavaScript PHP, and Ruby.
258
+
```
259
+
260
+
#### window Binding
261
+
262
+
When we’re not using `call`, `apply`, `bind`, or the `new` keyword, by default `this` will reference the `window` object. What that means is if we add an age property to the `window` object, then when we invoke our sayAge function, `this.age` will be whatever the age property is on the `window` object.
0 commit comments