2

According to Douglas Crockford I could use something like http://javascript.crockford.com/prototypal.html (with a little bit of tweaking)... but I am interested in jQuery way of doing it. Is it good practice using $.extend ?

I have 4 classes :

            var A = function(){ } 
            A.prototype = {
                name : "A",
                cl : function(){
                    alert(this.name);
                }
            }
            var D = function(){} 
            D.prototype = {
                say : function(){
                    alert("D");
                }
            }

            var B = function(){} //inherits from A
            B.prototype = $.extend(new A(), {
                name : "B"
            });

            var C = function(){} //inherits from B and D
            C.prototype = $.extend(new B(), new D(), {
                name : "C"
            });


            var o = new C();

            alert((o instanceof B) && (o instanceof A) && (o instanceof C)); //is instance of A, B and C 
            alert(o instanceof D); //but is not instance of D

So, i can call every method, property ... from A, B, C and D. Problem comes, when I want to test if o is instance of D? How can I overcome this problem?

2
  • Just a note, in practice, in a duck typed language, you rarely care if an object is instanceof something. Why are you checking instanceof D? Note that usually what you really need are en.wikipedia.org/wiki/Mixin Commented Mar 11, 2013 at 15:11
  • Multiple inheritance does not work with instanceof, since objects can only have a linear prototype chain. Commented Mar 11, 2013 at 16:11

2 Answers 2

4

Is it good practice using $.extend

$.extend is useful for singletons but for prototypes is not ideal.

Using Object.create (or Crockford's polyfill) you can easily create classes like this. I'm using $.extend to simply process the properties and give them default values and the module pattern to keep it well organized. Hope this helps:

// Helper that makes inheritance work using 'Object.create'
Function.prototype.inherits = function(parent) {
  this.prototype = Object.create(parent.prototype);
};

var Person = (function PersonClass() {

  var _defaults = {
    name: 'unnamed',
    age: 0
  };

  function Person(props) {
    $.extend(this, props, _defaults);
  }

  Person.prototype = {
    say: function() {
      return 'My name is '+ this.name;
    }
  };

  return Person;

}());

var Student = (function StudentClass(_super) {

  Student.inherits(_super); // inherit prototype

  var _defaults = {
    grade: 'untested'
  };

  function Student(props) {
    _super.apply(this, arguments); // call parent class
    $.extend(this, props, _defaults);
  }

  Student.prototype.say = function() {
    return 'My grade is '+ this.grade;
  };

  return Student;

}(Person));

var james = new Student({ name: 'James', grade: 5 });

console.log(james instanceof Student); // true
console.log(james instanceof Person); // true
Sign up to request clarification or add additional context in comments.

1 Comment

very good example. tnx. it gave me new point of view on things. i've decided to stick with method described here : javascript.crockford.com/prototypal.html for now. but is there a way to use multiple inheritance at once with clean coding?
1

An object has only one prototype, so you cannot make it an instance of two other types with one call.

$.extend(new B(), new D(), ... creates an object that is an instance of B. Then all properties of D are copied to the newly created object. But the object will still be an instance of B.

Using $.extend is neither good nor bad per se. But you are bound to jQuery, which makes your code less reusable. And you have to be aware of the fact that $.extend overwrites properties with the same name, which might or might not be what you want.

4 Comments

tnx for the answer! i thought there is a way to use multiple inheritance at once with clean coding?
Well, multiple inheritance is the opposite of clean coding ;) If instanceof is not absolutely necessary for you then your code is fine. There is no way, sorry.
can you look under answers. If you could inspect it... EDIT: ok i can not answer my own question. so here is ouside link : jsfiddle.net/Rfzzr
That's essentially what $.extend does. The difference is that this code creates a new type.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.