1

On MDN they state the following:

Properties are variables contained in the class; every instance of the object has those properties. Properties should be set in the prototype property of the class (function) so that inheritance works correctly.

Looking at the sections I've set to bold I assumed this meant:

myClass.prototype.newProperty = ...

However their example shows the following:

function Person(firstName) {
  this.firstName = firstName;
  console.log('Person instantiated');
}

var person1 = new Person('Alice');
var person2 = new Person('Bob');

// Show the firstName properties of the objects
console.log('person1 is ' + person1.firstName); // logs "person1 is Alice"
console.log('person2 is ' + person2.firstName); // logs "person2 is Bob"

In their example they're adding the property 'firstName' directly to the class/function using 'this'.

Does this mean:
a) That the function declaration is the prototype? I.e. myClass is the prototype which also has a property prototype which by default is set to Object?
b) That using 'this.' in the function declaration does actually add the property to the myClass.prototype

Edit: Updated title

Jacques
  • 6,936
  • 8
  • 43
  • 102
  • Prototype is shared and usually behavior or immutable default data members. this.someProp is instance specific explained in detail here: http://stackoverflow.com/questions/16063394/prototypical-inheritance-writing-up/16063711#16063711 – HMR Oct 31 '14 at 10:13
  • That sentence appears to be rubbish. Where exactly do they state that? Either we miss it's context, or it should be fixed. – Bergi Oct 31 '14 at 14:57
  • @Bergi The comment can be found here: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Introduction_to_Object-Oriented_JavaScript – Jacques Nov 03 '14 at 06:07
  • Thanks. It's indeed wrong and misleading - [I've fixed it](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Introduction_to_Object-Oriented_JavaScript$compare?to=688841&from=688603) – Bergi Nov 03 '14 at 12:52

1 Answers1

2

JavaScript doesn't have classes, stop thinking in classes, because that doesn't work with JavaScript (yes, even with the ES6 class syntax, it's just sugar, there aren't actual classes in JavaScript).

By adding the property to the object's prototype, you ensure that it and any other objects with the same prototype will share this property, this means that they'll all have it, but it also mean that if you change it on one, it will change with all of them. Oops.

The creation of a new object with the new keyword is fairly straightforward:

  1. Create an empty object
  2. Make that object prototype the same prototype as the constructor's
  3. Call the constructor with this as the newly created object.

So adding a property to the prototype of an object will have it shared among all instances of the same constructor, while adding it to this in the constructor will have it only on this specific instance. Because it's set in the constructor, it's safe to assume that all instances will have that variable in them, although it won't be shared with all other instances.

When you call a JavaScript property, the engine will look for it in the following fasion:

  1. Look for the property on the object itself (that's this inside of methods of that object)
  2. If not found, look for the property on the object's prototype
  3. If not found, go up the prototype chain and look for it there

So in your Person example, the lookup chain will look like:

this > Person.prototype > Object.prototype

The constructor's will look like this:

this > Person.prototype > Function.prototype > Object.prototype

Person is a function, so its prototype is inherited from Function.prototype, similarly any function is an Object.

So to your specific questions:

  1. The function declaration is not the prototype. See the object creation process above.
  2. No, this applies the property on this instance, while prototype is shared among all instances.
Madara's Ghost
  • 172,118
  • 50
  • 264
  • 308
  • Thanks. I used the word class only because MDN referred to it. In truth I do come from a C# background so my view is somewhat warped. This is why I'm going through various bits and pieces of documentation, to understand how to properly use OOP in JavaScript and not get lost in the C# vs. JavaScript implementations thereof. – Jacques Oct 31 '14 at 10:07
  • Incidentally, in defining a language as OOP the notion of a class is considered as something having attributes and behaviours. In your reply you made use of many other OOP terminology such as Object, Constructor, Inheritance, etc. where a constructor is actually the same function as what would be considered an OOP 'class'. I'm trying not to think in C# but rather in terms of OOP, which leads me to think that your constructor function is in essence, and by OOP standards, a class. I recon the problem comes in where people confuse the implementations. – Jacques Oct 31 '14 at 10:16
  • Try to rid yourself of thinking in classes when developing JavaScript OOP. Objects inherit from other Objects, not from classes. If you can get that to 'click' inside your mind, you'll have an easier time :) – Madara's Ghost Oct 31 '14 at 10:17
  • Second Rikudo, actually each instance of Person has a prototype chain like so: `this > Person.prototype > Object.prototype` and the Person constructor has a chain like so: `Person > Function.prototype > Object.prototype`. – istos Oct 31 '14 at 10:19