borrowing costructors and prototype chain - javascript

in many books and online tutorial there are examples on passing data to a super-class
constructor via a borrowing method pattern:
var Parent = function(name)
{
this.name = name;
this.my_parent = "parent_property";
this.go = function()
{
alert("GO")
}
}
var Child = function(name)
{
this.name = name;
this.my_child = "child_property";
Parent.call(this);
alert(this.hasOwnProperty("go")) // HERE TRUE!!!
}
var ChildChild = function(name)
{
this.name = name;
this.su = function(){}
}
// PSEUDO CLASSICAL ECMA STANDARD
Child.prototype = new Parent("PARENT");
ChildChild.prototype = new Child("CHILD");
var c = new ChildChild("CHILDCHILD");
now my question is: is this correct? in that pattern the properties of the super-class
are copied into THIS but in a OOP system I think that those properties must be in its
super-class. Now BORROWING constructor is only another pattern to make a sort of inheritance so I could not use prototype and so all the chain superclass properties are
into the last child class...but I don't think it's efficient.
So, at end, how can I pass data to a super-class without that pattern?
Thanks

By calling .call() you don't inherit in the classical sense of the word instead you tell Child to apply Parents prototype onto itself and thus Child.prototype has cloned properties and methods from Parent. This has no issues performance wise whatsoever though so abandoning prototype for efficiency reasons is not a valid reason.
If I can be honest I think enforcing OO paradigms onto javascript is the biggest mistake a javascript developer can make. Much like having to learn to deal with immutability in functional programming trying to make javascript behave like classical OO will only work against you in the long run.
It doesn't answer your question but there's tons of different ways to apply a super functionality to javascript none of which I can recommend though as there's no definitive version that doesn't come with a downside somewhere down the line.

JavaScript has no inherent support for building inheritance hierachies. The JavaScript way of doing type extensions would be to add properties from the 'parent class' to the 'child class', ie
function Parent(foo) {
this.foo = foo;
}
Parent.prototype.sharedFoo = 'sharedFoo';
function Child(foo, bar) {
// call the parent constructor
Parent.call(this, foo);
this.bar = bar;
}
Child.prototype.sharedBar = 'sharedBar';
// copy the properties of the parent class
for(var prop in Parent.prototype) {
if(Parent.prototype.hasOwnProperty(prop))
Child.prototype[prop] = Parent.prototype[prop];
}
It's also easily possible to add true prototypical inheritance, for example like this.
Via use of the clone() function, it's now possible to let the prototype object of the 'child class' inherit from the prototype object of the 'base class':
function Parent(foo) {
this.foo = foo;
}
Parent.prototype.sharedFoo = 'sharedFoo';
function Child(foo, bar) {
// call the parent constructor
Parent.call(this, foo);
this.bar = bar;
}
// inherit from the parent class
Child.prototype = clone(Parent.prototype);
Child.prototype.sharedBar = 'sharedBar';

JavaScript is a prototype based, functional language that pretends to be the cousin of Java.
Here is a few key things about JavasSript:
Everything is an Object, including Functions
Object is more like Hash, it is a collection of key value pairs
prototype itself is Object as well
To answer your first question about performance of "borrowing" prototype:
Typically, a JavaScript class contains a collection of [name, function object] pairs. When you borrow the prototype of the parent class, you basically copy the values of the parent prototype object into child class's prototype object.
The copy is by reference, when the function is copied, the function code is not duplicated, only the reference is copied. This is similar to function pointers in C language.
Thus the only performance hit is the
duplication of the prototype object,
which takes very little memory.
To answer your second question of how to pass data to Parent Class in a clean way:
There are many libraries out there that has some OOP style inheritance already built in. You can roll your own as well, but that would not be trivial.
I recommend a framework called Joose.
It supports classes, inheritance, mixins, traits, method modifiers and more.
Stable and used in production environments.
Elegant, and will save you a lot of key strokes
Using Joose, parent constructors can be overridden
or augmented, and SUPER() or INNER()
methods will be provided to access the
original constructor, or the subclass
constructor.

Related

Two ways of constructing an object in Javascript

function Person(age,name){
this.name = name;
this.age = age;
this.speak = function(){...}
}
function Person(age,name){
var p = {}
p.name = name;
p.age = age;
p.speak = function(){...}
return p;
}
The only difference I see is that using the first one you must call with new to let the language know its constructing a new object, is it essentially just constructing an object where 'this' refers to the new object being created??
i.e same as doing this.
{
age: 12,
name: "mark",
speak: function(){...}
}
where as the second returns an object so you can just write
Person(12,"mark")
instead of
new Person(12,"mark")
So I guess my question is, is there anything wrong with using the second version and are the differences I stated correct and are they the only differences between the two?
The first one:
function Person(age,name){
this.name = name;
this.age = age;
this.speak = function(){...}
}
Is a named constructor function.
Will work properly with instanceof Person
Is easier to do mixins or classic Javascript inheritance with
Could use the prototype for methods which may consume less memory or be faster to construct an object if there are lots of methods
Could also be designed to work without requiring new.
Is more akin to how the new ES6 class and extends syntax works which is likely how a lot of Javascript will be written in the future.
The second one:
function Person(age,name){
var p = {}
p.name = name;
p.age = age;
p.speak = function(){...}
return p;
}
Is a factory function. It creates a generic object, assigns properties to it and then returns the object.
It could be inherited from, but not in a classic way only by another factory function that knows how this object works. Some types of inheritance of mixins are not as doable with this structure.
Will not work with instanceof.
Does not and cannot use the prototype for methods.
Could be called with new and would still work (the system-created new object would just be discarded).
Can create any kind of object. It can even branch based on the arguments passed or environment and create a different kind of object based on some logic. Technically you can do this with the first style too, but it's inefficient because the interpreter creates a specific type of object and then you would return something else causing the original object that was created to then be garbage collected. So, if you're going to create multiple different kinds of objects, the second method would be more efficient at that.
Outside of these differences, the two will mostly function the same and there is nothing technically "wrong" with either method.
There are advocates for both styles of programming in Javascript and some would say there are situations where one is more appropriate than another and vice versa. I'd suggest you build a couple subclasses for this object to flush out some more of the programming differences because the subclasses will also work differently.
If you want to search for other articles on the topic, this is basically a "constructor function vs. a factory function in Javascript" which will sometimes stray into the argument for/against using the .prototype, but also tends to cover your topic too.
Here's are some articles on that specific topic (which cover a gamut of opinions):
JavaScript Constructor Functions Vs Factory Functions
Javascript object creation patterns
In defense of JavaScript’s constructors
Constructor function vs Factory functions
Factory constructor pattern
Some Useful JavaScript Object Creation Patterns
Constructors Are Bad For JavaScript
Constructors vs factories

understanding simple class emulator in JavaScript

Recently I started to learn a bit more advanced JavaScript (as far I only used jQuery for some simple tasks) and bought a book of Alex MaxCaw "JavaScript Web Applications". The first chapter treats about creating simple class emulator. I understand almost everything except for two lines of code marked with comments down below:
var Class = function(parent) {
var _class = function() {
this.init.apply(this, arguments);
};
if(parent) {
var subclass = function() {};
subclass.prototype = parent.prototype;
_class.prototype = new subclass();
};
_class.prototype.init = function() {};
_class.fn = _class.prototype;
//????
_class.fn.parent = _class;
//????
_class._super = _class.__proto__;
return _class;
};
Can anyone tell me what is purpose of these two lines? I'll be very thankfull.
Walking through the code:
Class is defined as a function that calls init with the arguments provided it. This means you can call it with standard constructor syntax using new eg. var instance = new Thingy() and get the init function called with the proper this value.
If you pass a parent class in, your class gets that class's prototype property added to the prototype chain of a new empty object which it uses as its prototype property. A more succinct way of doing this in modern browsers is _class.prototype = Object.create(parent.prototype);
The init function is defined. This should likely be overridden with more useful initialization code after a _class instance is created (or the code should be changed to allow the passing in of an init function when you create a Class... or allow the instance to walk the prototype chain to look for other init functions.
_class.fn is created to provide a reference to the _class constructor's prototype function.
_class.fn.parent is created to provide a reference back to the constructor. This may be useful if you are applying the prototype in some other context and want a reference back to the prototype's constructor.
_class._super is assigned the internal, non-standard __proto__ property of the constructor. Remember that constructors are functions and, in Javascript, functions are objects. This means they have their own internal prototypes. The earlier references to prototype are the prototype assigned to objects created with this constructor NOT the constructor's prototype itself. All functions inherit from Function.prototype, which is where they get bind, apply, etc. _super in this case is just a reference to Function.prototype.
As to when this type of _super is used, one could imagine doing the following:
function Maker(){ //this will be called as a constructor, ie. with new
var fun = function(){}; //Make a function
fun.__proto__ = this.__proto__; //yuck. Set the function's this value to the instance
return fun; //return the function
}
Maker.prototype={say:function(){console.log("Javascript is fun!.. And weird.")}};
var fun = new Maker();
fun.say() //"Javascript is fun!.. And weird."
console.log(fun.__proto__) // Object{say:function}
console.log(fun.bind) // undefined!!
Woah! What just happened?
In fact, you replaced your functions internal prototype with an Object. This allows you to build up interesting prototype chains and interact with both functions and objects in a similar way. Note, however, that the link with Function.prototype has been severed, which is why we don't have access to bind. However let's fix it with more prototype magic!
function FunctionConnector(obj){
for (var prop in obj){
if(obj.hasOwnProperty(prop){
this.prop=obj.prop
}
}
}
FunctionConnector.prototype=Function.prototype;
Maker.prototype=new FunctionConnector({say:function(){
console.log("Javascript is fun!.. And weird.")
}});
var fun = new Maker();
fun.say() //"Javascript is fun!.. And weird."
console.log(fun.__proto__) // Object{say:function}
console.log(fun.bind) // function bind(){ [native code] }
Now what is that FunctionConnector? It takes an object and, when called as a constructor, returns an object that both has all the properties of the passed object AND inherits from Function.prototype. As you can see, our access to bind has returned (Of course we also could have made do with our original implementation and just Function.prototype.bind.called our way to victory).
With this new pattern in hand it may be clearer what _super in your code does, namely it references the built in prototype of the _class constructor you are making (In our example the instance of FunctionConnector would be _super). This reference could be used to patch the prototype at runtime, call methods with apply or anything else you can due with a reference to an object.
This is, as you may have noticed a little hackish, especially since __proto__ is nonstandard. But it's also somewhat neat if you enjoy the patterns it allows. I'd recommend only doing something like this if you are very confident in your knowledge of Javascript inheritance, and perhaps not even then unless you are in charge of your entire code base.
From what i know, fn is just an alias to the prototype property
And about the _super, that one is for referencing to the "class" from which you are inheriting
Here's more about the use of _super and js inheritance: article

Can we assign a public method inside a object constructor ? (javascript)

I am reading about prototypes in javascript, In a article http://phrogz.net/js/classes/OOPinJS.html I read that we can not assign public methods inside a object constructor in javascript ? How prototypal methods are different from static methods and what are the advantage of using them ?
I read that we can not assign public methods inside a object constructor in javascript?
Yes, the article refers to this:
function MyObj(name)
{
this.name = name;
}
MyObj.prototype.sayHello = function() {
alert('hello ' + this.name);
}
new MyObj('world').sayHello();
As you can see, the public method sayHello() is declared in the prototype, which is done outside of the constructor. This is just how JavaScript works.
How prototypal methods are different from static methods and what are the advantage of using them ?
Prototypal methods are only "attached" to objects. For static methods you need to use this construct:
var MyStaticThing = {
name: 'world',
sayHello: function() {
alert('hello ' + this.name);
}
}
MyStaticThing.sayHello();
JavaScript isn't really well suited for most OOP concepts and paradigms, especially once you try to emulate inheritance. Rather than think of prototype vs "privileged" methods in OOP terms, you should think of things in terms of how JavaScript instantiates objects. Take this simple "class":
var id = 0;
function myClass()
{
var that = this;
id++; //closure, each new instance gets a unique id
this.id = id;
this.toString = function()
{
return that.id.toString();
}
}
And this class is instantiated like so:
var classInstance = new myClass();
This isn't a pattern I would necessarily recommend, the point is to illustrate that for each instantiation, each instance gets its own unique toString function. That means if you instantiate 100 classInstances, and you change toString on one of them to do something else, only that one instance will have that new functionality.
That also means that for every instance, every privileged method is also instantiated alongside with it. If you are instantiating a lot of instances, that can make a big performance difference. I had a case where I saw a measurable speed improvement by converting my privileged methods to prototype methods.
Speaking of prototype methods, here's what that might look like:
var id = 0;
function myClass()
{
id++; //closure, each new instance gets a unique id
this.id = id;
}
myClass.prototype.toString = function()
{
return this.id.toString();
}
In this case no matter how many myClasses you have, you only instantiate the toString method once. And if it changes, it changes for all myClasses.
Personally, I use privileged methods in most of my JavaScript classes because it looks cleaner and only bother with the prototype chain if I know it's going to be instantiated a huge number of times. Also being able to access private variables allows you to have some semblance of information hiding vs being forced to make any accessed variables public.
"the advantage of using them"...which one are you referring? Generally the advantage is going to be using a prototypal method (and object construction generally), over something like static or classical methods in javascript. The answer you are looking for is really too long to address here, but the short answer is that javascript is based off a prototypal object inheritance system (meaning objects can be created on the fly and may inherited one to the other), as opposed to a classical system (objects may only inherit from classes, i.e. Java, C++, etc.)
While you may create objects in javascript in a classical way -- because the language is that flexible -- it is a bad and confused way to do it. Prototypical object construction allows you do important and good things like data hiding, access to super methods, etc. Like I said this is a verbose subject, really to big to be taken on in a little text box.

If Javascript's native OOP is classless, what about the constructor? Doesn't that imply a class?

I think Javascript native OOP system is said to be classless, and is object-based, not class-based. But every example I see always start with a constructor similar to
function Person(name) {
this.name = name;
}
Just by using a constructor this way, doesn't this already imply a class is being used? (a class called Person)
Details:
If we can use
a.__proto__ = b;
on any Javascript platform, then I think it is classless. But we can't do that. If we want that behavior, we need to use
function F() { }
F.prototype = b;
a = new F();
and so, a constructor has to be used. So if constructor is such a cornerstone in Javascript, that means it is intended to be constructor of Person, Widget, etc, and these are classes.
The OOP in Javascript is slightly different from, for instance, the Java OOP.
The Javascript constructors do not refer to a class definition (so it is classless). Rather the constructor refers to a prototype. The base of the OOP in Javascript is the Object object (not the Object class), from where all the others objects are derived.
Prototyping grants you inheritance, and the possibility to extend an existing object with properties and methods.
I suggest you this article.
In your example:
function Person(name) {
this.name = name;
}
Mike = new Person('Mike');
the Person() function lets you create a new object prototyped on the Object object with a new property called name. Well, such a kind of function in Javascript oop is called a constructor.
Classless may be an inaccurate way to describe JavaScript's approach on OOP.
JavaScript does lack class definitions.
It also lacks a class-to-object correspondence.
You can't check if an object instantiated with a constructor such as Person is of class Person.
You can check if it contains the expected object members and conclude that it is of the expected class.
But if the object members have been changed along the way you're not going to get the desired/expected result.
TL;DR
JavaScript exposes constructors (appropriately named prototypes) as a manner in which you can define a template for constructing plain objects.
The important thing is that the end result of a prototype call is a plain object with some predefined members and not an object of a certain class .
It's good to think of javascript as a classless environment. If you think javascript classes you should be able to assume there's certain useful things you can do when there are classes and they're strictly enforced. However those certain useful things you cannot assume. The presence of something that looks like a constructor does not indicate you're creating a class.
For example, let's say you var dude = Person('Ashton Kutcher'). Now, when you dude instanceOf person, you get true. You assume you have the properties and methods of a person. What if some code comes along and says dude.personMethod = undefined. Now, while dude instanceOf person will still be true, the personMethod is no longer available.
You can think of javascript as having classes but it's a leaky abstraction. It's better to think of javascript as having a prototypal inheritance system when it comes to determining what something is and what you can expect of it.
More information here: http://javascript.crockford.com/prototypal.html
Create a class using the Object Constructor and prototyping can help us
in creating many instances of the class without redefining the object each time wee need it.
so in the above example
function Person(name)
{
this.name = name;
}
you can create two persons with different names.
example :
var personA = new Person();
personA.name = "james";
var personB = new Person();
personB.name = "Tom";
alert(personA.name + personB.name);
i suggest you reading this link will be helpful
http://www.javascriptkit.com/javatutors/oopjs2.shtml

javascript inheritance

I know there is a lot of similar questions are tons of great answers to this. I tried to look at the classical inheritance methods, or those closure methods etc. Somehow I consider they are more or less "hack" methods to me, as it doesn't really what the javascript is designed to do. (Welcome anybody correct me if I am wrong).
OK, as long as it works, I satisfy with the classical inheritance pattern like:
PARENTClass = function (basevar) { do something here; };
PARENTClass.prototype = { a: b, c: d}; // prototype is auto gen
// Inheritance goes here
CHILDClass = function (childvar) { do something; };
CHILDClass.prototype = new PARENTClass(*1); // Actual inheritance to the prototype statement
// Instance
CHILDInstance = new CHILDClass(whatever);
Above is somehow, to my understanding the inheritance of JS. But one scenario I have no idea how to implement, is that what if I want to do some initializing DURING object creation (ie, within constructor), and the new object can be used right away.... My illustration on problem might not be too clear, so let me use the following C# Psuedo to explain what I want to do:
class PARENT {
public PARENT (basevar) { ... }
}
class CHILD : PARENT {
public CHILD (basevar) : PARENT (basevar) // constructor of child, and call parent constructor during construct.
{ ... }
}
For some reason (like init. UI elements), putting them in constructor seems the best way to do. Anyone have idea on how can I do it.
PS: in the *1, I have no idea what I should put there.
PS2: The above situation I DID found the jquery.inherit library can do, I just wonder if not using library can achieve it.
PS3: Or my understanding is wrong. Since javascript is not intended to mimick OOP (that's why i call it hack), what is the "CORRECT" logic to implement this.
It is not a hack as such; JavaScript is a prototyped language, as defined by Wikipedia as where:
..classes are not present, and behavior reuse (known as inheritance in class-based languages) is performed via a process of cloning existing objects that serve as prototypes.
As it says, classes are not used in JavaScript; each object that you create is descended from the JavaScript Object; all objects in JavaScript have the prototype object, and all instances of objects you create 'inherit' methods and properties from their object's prototype object. Take a look at the MDC prototype object reference for more information.
As of this, when you call the line:
CHILDClass.prototype = new PARENTClass();
This allows the CHILDClass object to add methods and properties to its prototype object from the PARENTClass object, which creates an effect similar to the idea of inheritance present in class-based languages. Since the prototype object affects every instance created of that object, this allows the parent object's methods and properties to be present in every instance of your child object.
If you want to call your parent class's constructor in your child class's constructor, you use the JavaScript call function; this allows you to call the parent class's constructor in the context of the child class's constructor, therefore setting the newly prototyped properties in your child class to what they are set as in the parent class.
You also do not need to put anything where you have specified the *1, since that line is merely used to add the methods and properties to the child class's prototype object; however, bear in mind that it calls the parent class's constructor, so if there are any arguments that are fundamental in the operation of the parent class constructor, you should check that these are present so as to avoid JavaScript errors.
You can manually invoke the parent constructor in the subclass constructor like this:
CHILDClass = function (basevar) {
PARENTClass.call(this, basevar);
// do something;
};
The trick here is using the call method, which allows you to invoke a method in the context of a different object. See the documentation of call for more details.
JavaScript has no built-in support for inheritance hierarchies as type extension is supposed to be done via aggregation, ie adding desired functionality directly to the object itself or its prototype if the property is to be shared between instances.
Nevertheless, JS is powerful enough to make implementing other forms of object construction possible, including classical inheritance.
Given a clone function - which is enough to add 'true' prototypical inheritance, and not JavaScript's bastardization thereof - your exampe can be implemented like this:
function ParentClass(baseVar) {
// do stuff
}
// don't overwrite the prototype object if you want to keep `constructor`
// see http://joost.zeekat.nl/constructors-considered-mildly-confusing.html
ParentClass.prototype.a = 'b';
ParentClass.prototype.c = 'd';
function ChildClass(childVar) {
// call the super constructor
ParentClass.call(this, childVar);
}
// don't inherit from a ParentClass instance, but the actual prototype
ChildClass.prototype = clone(ParentClass.prototype);
ChildClass.prototype.e = 'f';
It's also possible to add some syntactic sugar for class-based inheritance - my own implementation can be found here.
The example from above would then read
var ParentClass = Class.extend({
constructor: function(baseVar) {
// do stuff
},
a: 'b',
c: 'd'
});
var ChildClass = ParentClass.extend({
e: 'f'
});
I've got a lightweight javascript OOP wrapper that provides 'Class-like' inheritance where you can override base methods or call base constructors or members.
You define your classes like this:
//Define the 'Cat' class
function Cat(catType, firstName, lastName)
{
//Call the 'Animal' constructor.
Cat.$baseNew.call(this, firstName, lastName);
this.catType = catType;
}
//Extend Animal, and Register the 'Cat' type.
Cat.extend(Animal, { type: 'Cat' }, {
hello: function(text)
{
return "meaoow: " + text;
},
getFullName: function()
{
//Call the base 'Animal' getFullName method.
return this.catType + ": " + Cat.$base.getFullName.call(this);
}
})
//It has a built-in type system that lets you do stuff like:
var cat = new Cat("ginger", "kitty", "kat");
Cat.getType() // "Cat"
cat.getBaseTypesAndSelf() // ["Cat","Animal","Class"]
cat.getType() // "Cat"
cat.isTypeOf(Animal.getType()) // "True"
var dynamicCat = Class.createNew("Cat", ["tab","fat","cat"])
dynamicCat.getBaseTypesAndSelf() // ["Cat","Animal","Class"]
dynamicCat.getFullName() // tab: fat cat
source code available at: Class.js
I also have more details in my blog post about OOP in javascript
Just thought I'd mention some of the issues with the classical pattern you're going for:
Reference vars on the super class(es) will be available as essentially statics on ALL instances. For example, if you have var arr = [1,2,3] in the super, and do instance_1.arr.push(4) instance_2.arr.push(5) ALL of these instances will "see" the changes.
So you solve 1. with Ayman's solution which Zakas calls "Constructor Stealing", but now you call the constructor twice: once for your prototype and once for the constructor stealing. Solution - for your prototype use a helper like inheritPrototype (I showed the whole implementation of this in this post: inheritPrototype method FWIW, this essentially came from a combination of page 181 of Zakas's book and some Crockford study.
No privacy (but then again, you'd need to use something like the Durable Object pattern to get this and that may not be what you want)
Object definition is left "dangling": Solution - put an if statement checking for any of your prototype's functions and then define the prototype with a prototype literal.
I have running examples of all of this on github!!!
It's been just as much of a challenge for me to truly grok both: Zakas and Crockford books on object creation and inheritance. I also needed to try some different JavaScript TDD frameworks. So I decided to create an essay on both TDD Frameworks and JavaScript Object Creation & Inheritance. It has running code and jspec tests! Here's the link:*
My GitHub Open Source Essay/Book

Categories

Resources