How does JavaScript .prototype work?

505,437

Solution 1

Every JavaScript object has an internal "slot" called [[Prototype]] whose value is either null or an object. You can think of a slot as a property on an object, internal to the JavaScript engine, hidden from the code you write. The square brackets around [[Prototype]] are deliberate, and are an ECMAScript specification convention to denote internal slots.

The value pointed at by the [[Prototype]] of an object, is colloquially known as "the prototype of that object."

If you access a property via the dot (obj.propName) or bracket (obj['propName']) notation, and the object does not directly have such a property (ie. an own property, checkable via obj.hasOwnProperty('propName')), the runtime looks for a property with that name on the object referenced by the [[Prototype]] instead. If the [[Prototype]] also does not have such a property, its [[Prototype]] is checked in turn, and so on. In this way, the original object's prototype chain is walked until a match is found, or its end is reached. At the top of the prototype chain is the null value.

Modern JavaScript implementations allow read and/or write access to the [[Prototype]] in the following ways:

  1. The new operator (configures the prototype chain on the default object returned from a constructor function),
  2. The extends keyword (configures the prototype chain when using the class syntax),
  3. Object.create will set the supplied argument as the [[Prototype]] of the resulting object,
  4. Object.getPrototypeOf and Object.setPrototypeOf (get/set the [[Prototype]] after object creation), and
  5. The standardized accessor (ie. getter/setter) property named __proto__ (similar to 4.)

Object.getPrototypeOf and Object.setPrototypeOf are preferred over __proto__, in part because the behavior of o.__proto__ is unusual when an object has a prototype of null.

An object's [[Prototype]] is initially set during object creation.

If you create a new object via new Func(), the object's [[Prototype]] will, by default, be set to the object referenced by Func.prototype.

Note that, therefore, all classes, and all functions that can be used with the new operator, have a property named .prototype in addition to their own [[Prototype]] internal slot. This dual use of the word "prototype" is the source of endless confusion amongst newcomers to the language.

Using new with constructor functions allows us to simulate classical inheritance in JavaScript; although JavaScript's inheritance system is - as we have seen - prototypical, and not class-based.

Prior to the introduction of class syntax to JavaScript, constructor functions were the only way to simulate classes. We can think of properties of the object referenced by the constructor function's .prototype property as shared members; ie. members which are the same for each instance. In class-based systems, methods are implemented the same way for each instance, so methods are conceptually added to the .prototype property; an object's fields, however, are instance-specific and are therefore added to the object itself during construction.

Without the class syntax, developers had to manually configure the prototype chain to achieve similar functionality to classical inheritance. This led to a preponderance of different ways to achieve this.

Here's one way:

function Child() {}
function Parent() {}
Parent.prototype.inheritedMethod = function () { return 'this is inherited' }

function inherit(child, parent) {
  child.prototype = Object.create(parent.prototype)
  child.prototype.constructor = child
  return child;
}

Child = inherit(Child, Parent)
const o = new Child
console.log(o.inheritedMethod()) // 'this is inherited'

...and here's another way:

function Child() {}
function Parent() {}
Parent.prototype.inheritedMethod = function () { return 'this is inherited' }

function inherit(child, parent) {
    function tmp() {}
    tmp.prototype = parent.prototype
    const proto = new tmp()
    proto.constructor = child
    child.prototype = proto
    return child
}

Child = inherit(Child, Parent)
const o = new Child
console.log(o.inheritedMethod()) // 'this is inherited'

The class syntax introduced in ES2015 simplifies things, by providing extends as the "one true way" to configure the prototype chain in order to simulate classical inheritance in JavaScript.

So, similar to the code above, if you use the class syntax to create a new object like so:

class Parent { inheritedMethod() { return 'this is inherited' } }
class Child extends Parent {}

const o = new Child
console.log(o.inheritedMethod()) // 'this is inherited'

...the resulting object's [[Prototype]] will be set to an instance of Parent, whose [[Prototype]], in turn, is Parent.prototype.

Finally, if you create a new object via Object.create(foo), the resulting object's [[Prototype]] will be set to foo.

Solution 2

In a language implementing classical inheritance like Java, C# or C++ you start by creating a class--a blueprint for your objects--and then you can create new objects from that class or you can extend the class, defining a new class that augments the original class.

In JavaScript you first create an object (there is no concept of class), then you can augment your own object or create new objects from it. It's not difficult, but a little foreign and hard to metabolize for somebody used to the classical way.

Example:

//Define a functional object to hold persons in JavaScript
var Person = function(name) {
  this.name = name;
};

//Add dynamically to the already defined object a new getter
Person.prototype.getName = function() {
  return this.name;
};

//Create a new object of type Person
var john = new Person("John");

//Try the getter
alert(john.getName());

//If now I modify person, also John gets the updates
Person.prototype.sayMyName = function() {
  alert('Hello, my name is ' + this.getName());
};

//Call the new method on john
john.sayMyName();

Until now I've been extending the base object, now I create another object and then inheriting from Person.

//Create a new object of type Customer by defining its constructor. It's not 
//related to Person for now.
var Customer = function(name) {
    this.name = name;
};

//Now I link the objects and to do so, we link the prototype of Customer to 
//a new instance of Person. The prototype is the base that will be used to 
//construct all new instances and also, will modify dynamically all already 
//constructed objects because in JavaScript objects retain a pointer to the 
//prototype
Customer.prototype = new Person();     

//Now I can call the methods of Person on the Customer, let's try, first 
//I need to create a Customer.
var myCustomer = new Customer('Dream Inc.');
myCustomer.sayMyName();

//If I add new methods to Person, they will be added to Customer, but if I
//add new methods to Customer they won't be added to Person. Example:
Customer.prototype.setAmountDue = function(amountDue) {
    this.amountDue = amountDue;
};
Customer.prototype.getAmountDue = function() {
    return this.amountDue;
};

//Let's try:       
myCustomer.setAmountDue(2000);
alert(myCustomer.getAmountDue());

var Person = function (name) {
    this.name = name;
};
Person.prototype.getName = function () {
    return this.name;
};
var john = new Person("John");
alert(john.getName());
Person.prototype.sayMyName = function () {
    alert('Hello, my name is ' + this.getName());
};
john.sayMyName();
var Customer = function (name) {
    this.name = name;
};
Customer.prototype = new Person();

var myCustomer = new Customer('Dream Inc.');
myCustomer.sayMyName();
Customer.prototype.setAmountDue = function (amountDue) {
    this.amountDue = amountDue;
};
Customer.prototype.getAmountDue = function () {
    return this.amountDue;
};
myCustomer.setAmountDue(2000);
alert(myCustomer.getAmountDue());

While as said I can't call setAmountDue(), getAmountDue() on a Person.

//The following statement generates an error.
john.setAmountDue(1000);

Solution 3

This is a very simple prototype based object model that would be considered as a sample during the explanation, with no comment yet:

function Person(name){
    this.name = name;
}
Person.prototype.getName = function(){
    console.log(this.name);
}
var person = new Person("George");

There are some crucial points that we have to consider before going through the prototype concept.

1- How JavaScript functions actually work:

To take the first step we have to figure out, how JavaScript functions actually work , as a class like function using this keyword in it or just as a regular function with its arguments, what it does and what it returns.

Let's say we want to create a Person object model. but in this step I'm gonna be trying to do the same exact thing without using prototype and new keyword.

So in this step functions, objects and this keyword, are all we have.

The first question would be how this keyword could be useful without using new keyword.

So to answer that let's say we have an empty object, and two functions like:

var person = {};
function Person(name){  this.name = name;  }

function getName(){
    console.log(this.name);
}

and now without using new keyword how we could use these functions. So JavaScript has 3 different ways to do that:

a. first way is just to call the function as a regular function:

Person("George");
getName();//would print the "George" in the console

in this case, this would be the current context object, which is usually is the global window object in the browser or GLOBAL in Node.js. It means we would have, window.name in browser or GLOBAL.name in Node.js, with "George" as its value.

b. We can attach them to an object, as its properties

-The easiest way to do this is modifying the empty person object, like:

person.Person = Person;
person.getName = getName;

this way we can call them like:

person.Person("George");
person.getName();// -->"George"

and now the person object is like:

Object {Person: function, getName: function, name: "George"}

-The other way to attach a property to an object is using the prototype of that object that can be find in any JavaScript object with the name of __proto__, and I have tried to explain it a bit on the summary part. So we could get the similar result by doing:

person.__proto__.Person = Person;
person.__proto__.getName = getName;

But this way what we actually are doing is modifying the Object.prototype, because whenever we create a JavaScript object using literals ({ ... }), it gets created based on Object.prototype, which means it gets attached to the newly created object as an attribute named __proto__ , so if we change it, as we have done on our previous code snippet, all the JavaScript objects would get changed, not a good practice. So what could be the better practice now:

person.__proto__ = {
    Person: Person,
    getName: getName
};

and now other objects are in peace, but it still doesn't seem to be a good practice. So we have still one more solutions, but to use this solution we should get back to that line of code where person object got created (var person = {};) then change it like:

var propertiesObject = {
    Person: Person,
    getName: getName
};
var person = Object.create(propertiesObject);

what it does is creating a new JavaScript Object and attach the propertiesObject to the __proto__ attribute. So to make sure you can do:

console.log(person.__proto__===propertiesObject); //true

But the tricky point here is you have access to all the properties defined in __proto__ on the first level of the person object(read the summary part for more detail).


as you see using any of these two way this would exactly point to the person object.

c. JavaScript has another way to provide the function with this, which is using call or apply to invoke the function.

The apply() method calls a function with a given this value and arguments provided as an array (or an array-like object).

and

The call() method calls a function with a given this value and arguments provided individually.

this way which is my favorite, we can easily call our functions like:

Person.call(person, "George");

or

//apply is more useful when params count is not fixed
Person.apply(person, ["George"]);

getName.call(person);   
getName.apply(person);

these 3 methods are the important initial steps to figure out the .prototype functionality.


2- How does the new keyword work?

this is the second step to understand the .prototype functionality.this is what I use to simulate the process:

function Person(name){  this.name = name;  }
my_person_prototype = { getName: function(){ console.log(this.name); } };

in this part I'm gonna be trying to take all the steps which JavaScript takes, without using the new keyword and prototype, when you use new keyword. so when we do new Person("George"), Person function serves as a constructor, These are what JavaScript does, one by one:

a. first of all it makes an empty object, basically an empty hash like:

var newObject = {};

b. the next step that JavaScript takes is to attach the all prototype objects to the newly created object

we have my_person_prototype here similar to the prototype object.

for(var key in my_person_prototype){
    newObject[key] = my_person_prototype[key];
}

It is not the way that JavaScript actually attaches the properties that are defined in the prototype. The actual way is related to the prototype chain concept.


a. & b. Instead of these two steps you can have the exact same result by doing:

var newObject = Object.create(my_person_prototype);
//here you can check out the __proto__ attribute
console.log(newObject.__proto__ === my_person_prototype); //true
//and also check if you have access to your desired properties
console.log(typeof newObject.getName);//"function"

now we can call the getName function in our my_person_prototype:

newObject.getName();

c. then it gives that object to the constructor,

we can do this with our sample like:

Person.call(newObject, "George");

or

Person.apply(newObject, ["George"]);

then the constructor can do whatever it wants, because this inside of that constructor is the object that was just created.

now the end result before simulating the other steps: Object {name: "George"}


Summary:

Basically, when you use the new keyword on a function, you are calling on that and that function serves as a constructor, so when you say:

new FunctionName()

JavaScript internally makes an object, an empty hash and then it gives that object to the constructor, then the constructor can do whatever it wants, because this inside of that constructor is the object that was just created and then it gives you that object of course if you haven't used the return statement in your function or if you've put a return undefined; at the end of your function body.

So when JavaScript goes to look up a property on an object, the first thing it does, is it looks it up on that object. And then there is a secret property [[prototype]] which we usually have it like __proto__ and that property is what JavaScript looks at next. And when it looks through the __proto__, as far as it is again another JavaScript object, it has its own __proto__ attribute, it goes up and up until it gets to the point where the next __proto__ is null. The point is the only object in JavaScript that its __proto__ attribute is null is Object.prototype object:

console.log(Object.prototype.__proto__===null);//true

and that's how inheritance works in JavaScript.

The prototype chain

In other words, when you have a prototype property on a function and you call a new on that, after JavaScript finishes looking at that newly created object for properties, it will go look at the function's .prototype and also it is possible that this object has its own internal prototype. and so on.

Solution 4

prototype allows you to make classes. if you do not use prototype then it becomes a static.

Here is a short example.

var obj = new Object();
obj.test = function() { alert('Hello?'); };

In the above case, you have static funcation call test. This function can be accessed only by obj.test where you can imagine obj to be a class.

where as in the below code

function obj()
{
}

obj.prototype.test = function() { alert('Hello?'); };
var obj2 = new obj();
obj2.test();

The obj has become a class which can now be instantiated. Multiple instances of obj can exist and they all have the test function.

The above is my understanding. I am making it a community wiki, so people can correct me if I am wrong.

Solution 5

The seven Koans of prototype

As Ciro San descended Mount Fire Fox after deep meditation, his mind was clear and peaceful.

His hand however, was restless, and by itself grabbed a brush and jotted down the following notes.


0) Two different things can be called "prototype":

  • the prototype property, as in obj.prototype

  • the prototype internal property, denoted as [[Prototype]] in ES5.

    It can be retrieved via the ES5 Object.getPrototypeOf().

    Firefox makes it accessible through the __proto__ property as an extension. ES6 now mentions some optional requirements for __proto__.


1) Those concepts exist to answer the question:

When I do obj.property, where does JS look for .property?

Intuitively, classical inheritance should affect property lookup.


2)

  • __proto__ is used for the dot . property lookup as in obj.property.
  • .prototype is not used for lookup directly, only indirectly as it determines __proto__ at object creation with new.

Lookup order is:

  • obj properties added with obj.p = ... or Object.defineProperty(obj, ...)
  • properties of obj.__proto__
  • properties of obj.__proto__.__proto__, and so on
  • if some __proto__ is null, return undefined.

This is the so-called prototype chain.

You can avoid . lookup with obj.hasOwnProperty('key') and Object.getOwnPropertyNames(f)


3) There are two main ways to set obj.__proto__:

  • new:

    var F = function() {}
    var f = new F()
    

    then new has set:

    f.__proto__ === F.prototype
    

    This is where .prototype gets used.

  • Object.create:

     f = Object.create(proto)
    

    sets:

    f.__proto__ === proto
    

4) The code:

var F = function(i) { this.i = i }
var f = new F(1)

Corresponds to the following diagram (some Number stuff is omitted):

(Function)       (  F  )                                      (f)----->(1)
 |  ^             | | ^                                        |   i    |
 |  |             | | |                                        |        |
 |  |             | | +-------------------------+              |        |
 |  |constructor  | |                           |              |        |
 |  |             | +--------------+            |              |        |
 |  |             |                |            |              |        |
 |  |             |                |            |              |        |
 |[[Prototype]]   |[[Prototype]]   |prototype   |constructor   |[[Prototype]]
 |  |             |                |            |              |        |
 |  |             |                |            |              |        |
 |  |             |                | +----------+              |        |
 |  |             |                | |                         |        |
 |  |             |                | | +-----------------------+        |
 |  |             |                | | |                                |
 v  |             v                v | v                                |
(Function.prototype)              (F.prototype)                         |
 |                                 |                                    |
 |                                 |                                    |
 |[[Prototype]]                    |[[Prototype]]          [[Prototype]]|
 |                                 |                                    |
 |                                 |                                    |
 | +-------------------------------+                                    |
 | |                                                                    |
 v v                                                                    v
(Object.prototype)                                       (Number.prototype)
 | | ^
 | | |
 | | +---------------------------+
 | |                             |
 | +--------------+              |
 |                |              |
 |                |              |
 |[[Prototype]]   |constructor   |prototype
 |                |              |
 |                |              |
 |                | -------------+
 |                | |
 v                v |
(null)           (Object)

This diagram shows many language predefined object nodes:

  • null
  • Object
  • Object.prototype
  • Function
  • Function.prototype
  • 1
  • Number.prototype (can be found with (1).__proto__, parenthesis mandatory to satisfy syntax)

Our 2 lines of code only created the following new objects:

  • f
  • F
  • F.prototype

i is now a property of f because when you do:

var f = new F(1)

it evaluates F with this being the value that new will return, which then gets assigned to f.


5) .constructor normally comes from F.prototype through the . lookup:

f.constructor === F
!f.hasOwnProperty('constructor')
Object.getPrototypeOf(f) === F.prototype
F.prototype.hasOwnProperty('constructor')
F.prototype.constructor === f.constructor

When we write f.constructor, JavaScript does the . lookup as:

  • f does not have .constructor
  • f.__proto__ === F.prototype has .constructor === F, so take it

The result f.constructor == F is intuitively correct, since F is used to construct f, e.g. set fields, much like in classic OOP languages.


6) Classical inheritance syntax can be achieved by manipulating prototypes chains.

ES6 adds the class and extends keywords, which are mostly syntax sugar for previously possible prototype manipulation madness.

class C {
    constructor(i) {
        this.i = i
    }
    inc() {
        return this.i + 1
    }
}

class D extends C {
    constructor(i) {
        super(i)
    }
    inc2() {
        return this.i + 2
    }
}
// Inheritance syntax works as expected.
c = new C(1)
c.inc() === 2
(new D(1)).inc() === 2
(new D(1)).inc2() === 3
// "Classes" are just function objects.
C.constructor === Function
C.__proto__ === Function.prototype
D.constructor === Function
// D is a function "indirectly" through the chain.
D.__proto__ === C
D.__proto__.__proto__ === Function.prototype
// "extends" sets up the prototype chain so that base class
// lookups will work as expected
var d = new D(1)
d.__proto__ === D.prototype
D.prototype.__proto__ === C.prototype
// This is what `d.inc` actually does.
d.__proto__.__proto__.inc === C.prototype.inc
// Class variables
// No ES6 syntax sugar apparently:
// http://stackoverflow.com/questions/22528967/es6-class-variable-alternatives
C.c = 1
C.c === 1
// Because `D.__proto__ === C`.
D.c === 1
// Nothing makes this work.
d.c === undefined

Simplified diagram without all predefined objects:

(c)----->(1)
 |   i
 |
 |
 |[[Prototype]]
 |
 |
 v    __proto__
(C)<--------------(D)         (d)
| |                |           |
| |                |           |
| |prototype       |prototype  |[[Prototype]] 
| |                |           |
| |                |           |
| |                | +---------+
| |                | |
| |                | |
| |                v v
|[[Prototype]]    (D.prototype)--------> (inc2 function object)
| |                |             inc2
| |                |
| |                |[[Prototype]]
| |                |
| |                |
| | +--------------+
| | |
| | |
| v v
| (C.prototype)------->(inc function object)
|                inc
v
Function.prototype

Let's take a moment to study how the following works:

c = new C(1)
c.inc() === 2

The first line sets c.i to 1 as explained in "4)".

On the second line, when we do:

c.inc()
  • .inc is found through the [[Prototype]] chain: c -> C -> C.prototype -> inc
  • when we call a function in Javascript as X.Y(), JavaScript automatically sets this to equal X inside the Y() function call!

The exact same logic also explains d.inc and d.inc2.

This article https://javascript.info/class#not-just-a-syntax-sugar mentions further effects of class worth knowing. Some of them may not be achievable without the class keyword (TODO check which):

Share:
505,437
John Leidegren
Author by

John Leidegren

Nothing is true; everything is permitted.

Updated on September 24, 2020

Comments

  • John Leidegren
    John Leidegren almost 4 years

    I'm not that into dynamic programming languages but I've written my fair share of JavaScript code. I never really got my head around this prototype-based programming, does any one know how this works?

    var obj = new Object();
    obj.prototype.test = function() { alert('Hello?'); };
    var obj2 = new obj();
    obj2.test();
    

    I remember a lot discussion I had with people a while back (I'm not exactly sure what I'm doing) but as I understand it, there's no concept of a class. It's just an object, and instances of those objects are clones of the original, right?

    But what is the exact purpose of this ".prototype" property in JavaScript? How does it relate to instantiating objects?

    Update: correct way

    var obj = new Object(); // not a functional object
    obj.prototype.test = function() { alert('Hello?'); }; // this is wrong!
    
    function MyObject() {} // a first class functional object
    MyObject.prototype.test = function() { alert('OK'); } // OK
    

    Also these slides really helped a lot.

    • John Foster
      John Foster over 15 years
      John Resig has a few slides on function prototypes that were helpful to me when looking into the subject (you can also make changes to the code and see what happens...) http://ejohn.org/apps/learn/#64
    • Chris
      Chris about 13 years
      Great reference material, for purposes of keeping this question informative perhaps place some of the comments from John's site on your answer in case his site is changes in a way that your link is no longer available. Either way +1, helped me.
    • a paid nerd
      a paid nerd about 12 years
      +1 for your link to John Resig's JavaScript Ninja slide #64. Starting from there was really helpful, and I feel like I understand prototypes correctly.
    • Anshul
      Anshul over 11 years
      Do we really need a functional object for applying prototype? if yes than why ?
    • Naor
      Naor about 11 years
    • user3167101
      user3167101 almost 11 years
      I wrote something that hopefully is clear enough: JavaScript's prototype property
    • Mathieu Larose
      Mathieu Larose almost 10 years
    • kazy
      kazy over 9 years
    • Yibo Yang
      Yibo Yang over 8 years
      A lot of the confusion (at least for me) comes from the somewhat dual meaning of "the prototype of a constructor function": it could mean either constructor.prototype or constructor.__proto__. Make sure you understand both
    • Codebeat
      Codebeat over 7 years
      Don't forget a semicollon ; after a declaration ;-)
  • some
    some over 15 years
    FF and Chrome supports proto, but not IE nor Opera.
  • Christoph
    Christoph over 15 years
    -1: prototype is a property of constructor functions, not instances, ie your code is wrong! Perhaps you meant the non-standard property __proto__ of objects, but that's a whole different beast...
  • stivlo
    stivlo over 13 years
    I think the answers on stackoverflow are not only interesting to the original poster, but also to a big community of other people lurking or coming from searches. And I've been one of them and I had benefit from old posts. I think I could contribute to the other answers adding some code examples. About your question: if you leave out the new, it doesn't work. when I call myCustomer.sayMyName() it returns "myCustomer.sayMyName is not a function". The easiest way is experiment with firebug and see what happens.
  • stivlo
    stivlo over 13 years
    As far as I understand var Person = function (name) {...}; is defining a constructor function capable of building Person Objects. So there is no Object yet, only the anonymous constructor function is assigned to Person. This is a very good explanation: helephant.com/2008/08/how-javascript-objects-work
  • Hamish Grubijan
    Hamish Grubijan over 11 years
    Georg, please clarify for a noob - "there is no difference between classes and instances in javascript." - could you elaborate? How does this work?
  • Aaren Cordova
    Aaren Cordova over 10 years
    WARNING: This answer neglects the fact that the parent class constructor is not called on a per instance basis. The only reason it works is because he did the exact same thing (setting the name) in both the child and parent constructor. For a more in depth explanation on common mistakes made when attempting inheritance in JavaScript (and a final solution), please see: this stack overflow post
  • Rafael Eyng
    Rafael Eyng almost 10 years
    About the Customer.prototype = new Person(); line, MDN shows an example using Customer.prototype = Object.create(Person.prototype), and states that 'A common error here is to use "new Person()"'. source
  • HMR
    HMR over 9 years
    Not always written on product on assignment. You're not making it very clear that instance specific members have to be initialized and shared members can go on the prototype. Especially when you have instance specific mutable members: stackoverflow.com/questions/16063394/…
  • Aravind
    Aravind over 9 years
    HMR: In your example in your answer, the ben.food.push("Hamburger"); line alters the prototype object's property due to the following: 1.) First ben.food is looked up, and any lookup action will simply lookup the scope chain. 2.) The push function of that ben.food object is executed. By writing mode in my answer, I mean when you explicitly set a value to it, as in: ben.food = ['Idly']; This will always create a new property(if not already there) on the product object, and then assign the value to it.
  • Aravind
    Aravind over 9 years
    HMR: Thank for your comment, it made me think and test my understanding.
  • HMR
    HMR over 9 years
    When re assigning ben.food it'll shadow the food member unless food is created using Object.defineProperty, Object.defineProperties or Object.create with second argument (so not always). You can even change prototype with (what looks like) a re assignment when you created a getter setter. When it comes to patterns of inheritance I understand the constructor function is hard to understand and has some major problems but it is good if you understand it. Inheritance in JavaScript doesn't begin and end with setting a prototype, initializes (constructors) are to be (re) used as well.
  • HMR
    HMR over 9 years
    Your answer is good in explaining prototype but could be mis interpreted by over simplifying inheritance in JavaScript and instance specific members. A lot of questions have been asked why mutating a prototype member on an instance affects other instances.
  • Palec
    Palec almost 9 years
    Revision 5 removed some useful info, including info on Object.create(). See revision 4.
  • sam
    sam almost 9 years
    @Palec what should I add back?
  • Palec
    Palec almost 9 years
    IMO at least the link to Object.create() docs, @sam. Links to __proto__ and Object.prototype would be nice enhancements. And I liked your examples of how prototypes work with constructors and Object.create(), but they were probably the long and less relevant part you wanted to get rid of.
  • lukeaus
    lukeaus almost 8 years
    great video reference
  • blackHawk
    blackHawk over 7 years
    from the all discussion what i get(came from classical inheritance) if i create constructor function and try to create instance of it using new operator i will only get methods and properties that was attach to proto object, therefore its necessary to attach all the method and properties to proto object if we want to inherit, m i right?
  • blackHawk
    blackHawk over 7 years
    from the all discussion what i get(came from classical inheritance) if i create constructor function and try to create instance of it using new operator i will only get methods and properties that was attach to proto object, therefore its necessary to attach all the method and properties to proto object if we want to inherit, m i right?
  • blackHawk
    blackHawk over 7 years
    from the all discussion what i get(came from classical inheritance) if i create constructor function and try to create instance of it using new operator i will only get methods and properties that was attach to proto object, therefore its necessary to attach all the method and properties to proto object if we want to inherit, m i right?
  • Nikita Vlasenko
    Nikita Vlasenko almost 4 years
    Child now has its own prototype, its __proto__ points to Tree - seems wrong. __proto__ points to Function.prototype and not to Tree.