Tom Tom - 2 months ago 7
Javascript Question

Inheritance in Javascript calling functions

somehow JS inheritance doesn't get in my head. I tried quite a few things now and for some reason I cannot add a method to an object that inherits.

See my try of defining

B.setC
that then is not available later somehow. Any hints?

cheers
Tom

A = function( value){
this.aValue = value;
}


B = function(value){
A.call(this, value);
this.bValue=value+value;
}

B.prototype = Object.create(A.prototype);//subclass extends superclass


B.setC = function(value){
this.c = value+value+value;
console.log("execution");
}

B.prototype.setD = function(value){
this.D = value+value+value+value;
console.log("execution");
}





x = new B("ConstructorParam");
x.setC("methodParam");// gives that setC is not a function
x.setD("methodParam");// works but I added setD to A not B

Answer

The confusion seems to come from this misunderstanding; quoting your comment:

Actually it isn't a typo. I want to add setC to B not A and if my understanding is right and to what I saw debugging in Chrome it is if I use B.prototype.setB then I add setB to the prototype of B aka A and not B . Or am I missing sth?

which is also shown by this comment in the question:

x.setD("methodParam");// works but I added setD to A not B

B.prototype is not A. B.prototype is an object that has A.prototype as its prototype. You correctly added setD to B.prototype; it isn't in any way added to either A or A.prototype.

If you want to use setC and setD the way you showed, you would put them either on B.prototype (so they are accessible on instances of B) or on A.prototype (so they're accessible on instances of A or B).

If we change B.setC = to B.prototype.setC =, make d lower case to match c, add some missing vars, and use shorter values when creating and calling the methods, we get this:

var A = function( value){
    this.aValue = value;
};

var B = function(value){
    A.call(this, value); 
    this.bValue = value + value;
};

B.prototype = Object.create(A.prototype);//subclass extends superclass

B.setC = function(value){
    this.c = value + value + value;
    console.log("execution");
};

B.prototype.setD = function(value){
    this.d = value + value + value + value;
    console.log("execution");
};

var x = new B("b");
x.setC("c");
x.setD("d");

Just after the last line of code, this is what we have in memory (minus a bunch of unnecessary details):

         +−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−+
         |                                                               |
         \ +−−−−−−−−−−−−−−−+                                             |
A−−−−−−−−−>|   function    |                                             |
           +−−−−−−−−−−−−−−−+                             +−−−−−−−−−−−−−+ |
           | prototype     |−−−−−−−−−−−−−−−−−−−−−−−−−−−−>|   object    | |    
           +−−−−−−−−−−−−−−−+                           / +−−−−−−−−−−−−−+ |    
                                                       | | constructor |−+
                                                       | +−−−−−−−−−−−−−+
         +−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−−+ |
         |                                           | |
         \ +−−−−−−−−−−−−−−−+                         | |
B−−−−−−−−−>|   function    |                         | |
           +−−−−−−−−−−−−−−−+    +−−−−−−−−−−−−−−−−−−+ | |
           | prototype     |−−−>|      object      | | |
           +−−−−−−−−−−−−−−−+  / +−−−−−−−−−−−−−−−−−−+ | |
                              | | constructor      |−+ |
                              | | setC: (function) |   |
                              | | setD: (function) |   |
                              | | [[Prototype]]    |−−−+
           +−−−−−−−−−−−−−−−+  | +−−−−−−−−−−−−−−−−−−+
x−−−−−−−−−>|    object     |  |
           +−−−−−−−−−−−−−−−+  |
           | aValue: "a"   |  |
           | bValue: "aa"  |  |
           | c: "ccc"      |  |
           | d: "dddd"     |  |
           | [[Prototype]] |−−+
           +−−−−−−−−−−−−−−−+ 

[[Prototype]] above is the name the spec uses for the "internal slot" of an object that contains its reference to its prototype object. In contrast, prototype, the property on functions (e.g., A.prototype), is just a normal property of functions that points to the object that new will use as the [[Prototype]] of the new object it creates if you use that function with new.


Just for completeness, here that is in ES2015+:

class A {
    constructor(value) {
        this.aValue = value;
    }
}

class B extends A {
    constructor(value) {
        super(value); 
        this.bValue = value + value;
    }

    setC(value) {
        this.c = value + value + value;
        console.log("execution");
    }

    setD(value) {
        this.d = value + value + value + value;
        console.log("execution");
    }
}

let x = new B("b");
x.setC("c");
x.setD("d");
Comments