24 comments

[ 5.0 ms ] story [ 64.6 ms ] thread
What are the differences between this and something like MooTools? What benefits does P.js offer?

(Note: I was only introduced to MooTools today, so I have limited knowledge about it.)

Mootools does all kinds of stuff. This just allows you to create classes in a traditional way with inheritance and super afaik
It seems that everyone wants to add classes to Javascript. I understand that prototype-based programming is a bit of a change from class-based programming, but this is starting to feel like wasted energy on a problem that does not need solving.

What benefits do developers get from using a 3rd-party library to create classes in a prototype-based OOP language? Why can't developers just learn that there is more than one style of OOP, and go with the flow?

Because, for many things one wants to accomplish, prototype-based programming is so verbose and error-prone. Adding a simple class-based abstraction over top (which doesn't hide the prototype features) gives you the best of both worlds.
Please, please read http://killdream.github.com/blog/2011/10/understanding-javas...

Prototypical inheritance as of ES5 is really not that hard. Here is the same example rewritten with prototypes: https://gist.github.com/1558929

(comment deleted)
Please, please realise most of us are not going to be able to use Object in ES5 till IE8 dies.
Well, how about this? I'm fairly certain it's ES 3 compatible.

https://gist.github.com/1559933

The original was 28 lines, this is 36 (mostly because I like white space).

I haven't ever really tried to emulate classes in JS, but this is probably how I would do it. The major difference is that this is written plain old Javascript rather than some special syntax - easier to understand.

Object.create has two parts: the "create a new object with this other object as its prototype" part and the "define properties" part. The first part can be easily reproduced in ES3 and it's the most useful part. It's really well explained in this article by Douglas Crockford http://javascript.crockford.com/prototypal.html.
This is why Pjs is so small - it's just prototypal inheritance, with the bad parts taken out. You have to know how prototypes work to use Pjs.
pjs certainly deserves props for being creative with the function passing, and variable context. I haven't seen that exact usage before.

It seems every couple weeks javascript class library named X is released, avoiding issue Y, and implementing fuctionality Z.

Using `prototype` isn't terribly far off from the class systems people keep creating, so I can pretty much assume a single class library is going to reach deep adoption anytime soon.

normally all you'd need is a 2 liner utility method to facilitate inheritance. For the rest you can use js as it is with it's actual language features which maybe a little verbose (my only lament so far) and prototypical based but you will begin to appreciate it in the long run. I don't like the exaggerated syntactic sugar that many libs bring in, that try to abstract and tuck away js as it is, making it pretend to be a class based language when it is not. That said, this particular lib's size and the direct problems it tries to solves are done so elegantly. It's hard to ignore the good job the author has done!
Pretty nice. Ends up being similar in structure to classes in coffeescript.

The very last lines worry me a bit though:

    // instantiate objects by calling the class
    MyClass() // => init!

    // allocate blank objects with `new`
    new MyClass // nothing logged
Having `MyClass()` and `new MyClass` behave differently is totally unwarranted and will cause lots of confusion.
Yeah, I'll admit that's a bit confusing. I did want to provide a way do something like Object.create in environments where it's not available. This way you can do `MySubclass.prototype = new MyClass` and not have to worry about the initializer.
(apologies for the double post)

Doing away with `new` in this way also has the added advantage of allowing people to create objects with varargs, which is impossible otherwise.

    new MyClass('bacon', 'eggs')
is perfectly possible, or am I misunderstanding your sentence?

How about exposing creation via `P.create`, `P.inherit` or something like it?

right, but say you had an `var array = ['bacon', 'eggs']`. You can call a function with these arguments with `fn.apply(null, array)` (yeah it's ugly but it's how it's done in JS). This doesn't work with the `new` keyword.

EDIT: also, a class method would hurt your script's minifier performance. ...and at that point you may as well just call the function anyways :)

Pjs may work for a small number of objects, but if you're dealing with a large number of intances from a single class Pjs is going to use much more memory than needed. That's because the recommended method P(function () { this.method = fn; }) is declaring all methods as instances properties instead of using the prototype, so all methods are actually new functions in new own properties instead of properties of a shared object (the prototype).
I should have mentioned it in the README, but if you read carefully, the function you pass to P() is only called once, and you're adding functions to the prototype. So it's actually pretty memory-efficient.
Very interesting! I'll re-read the code.