Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Javascript inheritance question

Why Version 2 in the code below does not produce the same result as Version 1 ?

function person(name) {
    this.name = name;
}
function student(id, name) {
    this.id = id;
    // Version 1
    //this.inherit_from_person = person;
    //this.inherit_from_person(name);
    // Version 2
    person(name);
}
s = new student(5, 'Misha');
document.write(s.name); // Version 1    =>    Misha
                        // Version 2    =>    undefined

Live demo here.

like image 371
Misha Moroshko Avatar asked Jan 19 '23 20:01

Misha Moroshko


2 Answers

When you call person(name) it gets called with this bound to the global object, so that's just setting window.name = "Misha". You want person.call(this, name) to explicitly bind it to the right this.

like image 162
Boris Zbarsky Avatar answered Jan 28 '23 07:01

Boris Zbarsky


It looks to me like you are trying to implement prototype inheritance. Below is a classic example, though not much used. Complex inheritance is just not needed in javascript, usually a single instance is all that is required. If multiple instances are required, the module pattern can be used with closures for shared methods and properties and also to provide private and priveliged members.

// Person is the "base class"
function Person(name) {
  this.setName(name);
}

// Use setters and getters so properties are
// added appropriately.
Person.prototype.setName = function(name) {
  this.name = name;
}

// Add Person methods
Person.prototype.getName = function() {
  return this.name;
}

// Student inherits from Person and also has
// its own methods
function Student(name, id) {
  this.setId(id);
  this.setName(name);
}

// To inherit from Person, Student.prototype should
// be an instance of Person
Student.prototype = new Person();

// Add Student methods
Student.prototype.setId = function(id) {
  this.id = id;
}
Student.prototype.getId = function() {
  return this.id;
}

var p0 = new Student('Sally', '1234');
var p1 = new Person('James');

alert('p0\'s id is ' + p0.id + ' and name is: ' + p0.name);
alert('p1\'s name is: ' + p1.name);
alert('Is p0 a student? ' + (p0 instanceof Student));
alert('Is p1 a student? ' + (p1 instanceof Student));

Note that the instanceof operator is not very reliable, but it works fine in the above case. Also all methods and properties are public so easily over written.

like image 43
RobG Avatar answered Jan 28 '23 06:01

RobG