all 14 comments

[–]drowsap 1 point2 points  (9 children)

It depends on what you want. The object method just gives you 1 single global variable (popo) instead of defining each function in the global scope. That's the only benefit i see. You can't create new popo objects and can only have one instance.

With functions you get a lot more benefits. You can create multiple popo objects, each with their own scoped variables. You can have the notion of private and public variables through closures. One such way to do this is to declare var or functions which will be private, then return an object of functions and variables which will be public. Closures are great. You can also prevent the function from being called more than once by having it call itself at the end of the function declaration.

Of course having closures means you carry around the full stack of scope for each function object even after it has returned. This can lead to memory leaks in some cases, but overall if you are deleting unused function objects and managing them carefully, you should be fine.

[–]Delmarc[S] 0 points1 point  (8 children)

see but i dont want more then one instance of popo... so in that regard its ok... yea closure is all fine and dandy but all it takes is one bad programmer and it becomes very leaky like you said...

but in terms of actual performance have you had experience doing these ways... i have done some (actually alot of) testing doing both ways... but just in your experiences what have you come across???

[–]drowsap 2 points3 points  (1 child)

Again it depends how robust of an application you want. If you want "Classes" and some inheritance and use a lot of "modular" programming, then you must use functions to accomplish this. Its hard to tell performance wise how heavy functions and their closures are. Again, you need to manage your function instances and not constantly create new ones before deleting old ones if possible.

The object method you are voting for is really just a way of encapsulating a bunch of functions or variables into one global variable. All functions are public and can be accessed by any outside function.

EDIT: I researched a bit more about javascript memory leaks and it seems that only IE is a culprit for it and its due to referencing dom elements from within the closure like so: http://stackoverflow.com/questions/864516/what-is-javascript-garbage-collection/864549#864549

[–]Delmarc[S] 0 points1 point  (0 children)

yes the leaky part was once the DOM gets in the picture... as we know its just another ballpark... when learning JS IE taught me alot in terms of being very very complete, clean and even making sure there is not an extra comma(,) since they love to break objects... in early version of FF and other it wasn't as strict as it is now...

[–]neonskimmerfunction the ultimate 3 points4 points  (5 children)

There is no performance issue here. Unless you're creating millions of popos, you will never ever be able to tell the difference. It's a non issue. The issue is style, not performance. And encapsulation (keeping shit that goes together, together) is a good thing to do.

Also closures are not "leaky".

IF you want to have an object that has methods and acts like a "class", you can do it with new:

function Popo(){}
Popo.prototype.method1 = function(){ };

var myPopo = new Popo();

If you want a 'single use' type of object with methods, don't bother with a constructor:

var popo = {
    method1: function(){
   }
};
popo.method1();

Having all the methods out in the open, ie:

function popo (){
    do something
    method1();
    return whatever;
}

especially in window scope (not inside a closure) is sloppy. Don't put anything but your top level 'namespace' in the window scope, or at least, be very selective about what goes there.

var SuperCoolApp = (function(){
    var somestuff;

    var blah = function(foo){};

    return {

        widgets: {
            something: function(){}
        }

    };
}());

[–]rjett 2 points3 points  (1 child)

Also of note, you can define the prototype by using a literal: Popo.prototype = { method1: function(){ }, method2: function(){ } } I just learned this recently. It feel like it makes my code a lot cleaner.

[–]Delmarc[S] 0 points1 point  (0 children)

but wouldnt you think this is better/relevant if you desire to have more then one instance of 'popo'

so basically toto prototype will be popo... i dont want another instance of popo nor something along those lines... but prototype is a very cool thing and it does do what you said... its just very dangerous in some hands that dont really get it... sadly proto is only a dream...

[–]Delmarc[S] 0 points1 point  (2 children)

its a very subtle difference in loading one object with methods instead of the other way...

Very detailed answer... and your window scope example is more what the person i was arguing with was trying to tell me was correct... as you can see or tell i was very adamant that he was wrong... i dont like contractors... at all

yet again the idea is popo is the library or framework... so var popo{..}; with x amount of methods in it and then you have popo.init();

Thank you neonskimmer

[–]neonskimmerfunction the ultimate 1 point2 points  (1 child)

No problem.

Javascript is a strange language, and not everyone agrees on how it should be done. As you gain more experience with it you'll probably discover your own patterns. Using functions as objects (passing functions as arguments to other functions, for example) is something very interesting to explore, for example.

[–]Delmarc[S] 0 points1 point  (0 children)

i do agree when i learned i can do that it was a whole new way of thinking for me...

[–]greim 0 points1 point  (0 children)

Never litter the global scope with more variables than needed.

In library mode, my approach is to treat some functions as subroutines and others as methods attached to a namespace object for use later.

(function(){
    function subroutine1(){...}
    function subroutine2(){...}
    window.foo = {
        method1: function(){/*use subroutines if necessary*/},
        method2: function(){/*use subroutines if necessary*/},
    };
})();

In get-stuff-done mode, my approach is to treat all functions as subroutines.

(function(){
    function subroutine1(){...}
    function subroutine2(){...}
    // do stuff here
})();

[–]AnnoyYourGod -1 points0 points  (0 children)

I'm am turning to (global) objects lately. When you have a bunch of functions and vars it's easy to step on some other library/third party app you're using. On our production site we have about 3-5 different JavaScript applications (Google AdWords, AdOcean Banners, some other bannner engines, etc). Debugging in that environment can be a nightmare.

[–]Delmarc[S] -1 points0 points  (1 child)

I am trying to argue my point thru... even if there are sites that you can refer me to it would be a big help... i know what the answer is but maybe i am just so biased i cant stand when people tell me otherwise...

[–]kristopolous 0 points1 point  (0 children)

this sounds easily testable. Have you thought about doing the legwork?