What Is Wrong

every setTimeout() call will create a new bound object and this is both redundant and inefficient plus it's not GC friendly

there is no way to retrieve that listener created inline so it's impossible to remove the listener any time is necessary ... yes, even after, when you do refactoring 'cause you will need to clean up listeners

What You Need

The short version is less than a tweet, 64bytes: function b(o,s,t){return(t=this)[s="@"+o]||(t[s]=t[o].bind(t))}
This is the equivalent of:

you can remove the listener at any time through the same call, i.e. (objOrEl || this).removeEventListener(type, this.bound("method"), false);

Is That It ?

You are free to over complicate this concept as much as you want as long as you got the point: there's no need to create a new bound Object per each call plus your life will be much easier following this pattern focusing on logic rather than possible typos, boring variable assignments, etc etc ... this works and it's what you need and what you want now.
I'm also moving my hands as a Jedi so I hope I've convinced you!

Saturday, November 03, 2012

Many times I read or write silly stuff and often it takes a while before I realize "what dafuq did I just read ?"
Well, this post is about just few a-ha moments, together with WTFs, I keep having from time to time: enjoy!

Those 4 Repeated + Disturbing Bytes

I mean, this must come first, right? Web Development Tools are improving like hell and Web App development are 99% of the time behind a build process able to shrink HTML, recompile and optimize CSS, eliminate even death code from JS after parsing, recompilation, minification, pre-gzip-compression ... you name it ... and finally, we gonna have the output with a file called: mystuff.min.js ?!?!
Am I the only one thinking that this does not make sense and all files should be named by default .max so that the equivalent after minifcation won't include those damn 4 bytes per each file?
Entire CDN dedicated to common libraries and these expose minified files with .min extension ... isn't this bloody brilliant?

The "Not So Smart" Condition

This time is about logic, and the fact that order matters. "Which order?" you say? Thanks for asking!

Above code might look weird but it's actually more common than we can imagine.
Think about defining, as example, a prefixed method so that only one of them will be available. As soon as the value is not undefined we keep going checking for no reason something we don't need so ... can you spot the difference?

If fValue has a value there is no reason to perform other expensive function calls. Moreover, how can we be that lazy that breaking a for loop is one of those things I basically never see in production code ?

Scary ... uh ? Point here is: always think about the execution order, logic, cost of your boolean expressions ... you might realize swapping few things around could result in better performance easily while adding a break, sometimes, will be smarter than anything else.

Not Just Missing The Falsy

This is the most common one, no way JS developers will learn this differently. I have tried many times but there's nothing to do, bad habits are bad habits!
Let's see what I am talking about ...

obj.prop = obj.prop || defProp;

Can anyone answer exactly what are we trying to do up there? ^_^
Don't bother, here the summary and ... NO, we are not trying to do what we think!

access a possibly undefined property to a generic object

if that was a getter, invoking a getter of that object

either getter or property, verifying after lookup that value is not "", 0, false, NaN, null, or undefined

even if defined, discarding any of previous valid values in order to lookup for the variable defProp, assuming this won't have similar values we already discarded or the sequence could be infinitely pointless if repeated

once a value has been addressed, if any, assign as the property of the object

if this has a setter, invoke the setter for no reason potentially reacting for no reason as property update.

if the prop had a getter only, we have simply raised an Error ^_^ and without any valid reason

Nobody Uses Getters/Setters Anyhow

Excuse me? It's even worst than we think since one of the most powerful, cool, useful, tools ever for JS has been approved in harmony: Object.observe().
Can you imagine a defProp as NaN by mistake so that these three lines will most likely cause three records notifications because we are using a dumb pattern to assign a property if not defined yet? ^_^

Just Brilliant, and moArover this habit is so common that whoever will decide to simulate Object.observe() through Proxy (I am already, stay tuned) will need to guard the Records creations and notifications avoiding redundant notification because developers keep reassigning for no reason!

As Easy As This

There, you better embrace this pattern or you gonna have bad time soon either with Proxy, already available, and Object.observe, specially when we don't know who created the object and how. So, once again, repeat with me: avoid property access and/or reassignment for no reason, no excuse!

Bitwise To The Rescue

Rather than understand them, we often avoid them ... well, we shouldn't. Bitwise are cool and let us make a lot of things.
These days we are discussing Collection#has(key) and Collection#contains(value) where latter one could be the equivalent, if it won't use identicalType() to -1 < arr.indexOf(value) or, as I can read in many source code, the boring arr.indexOf(value) !== -1.
How about if (~arr.indexOf(value)) { ... } to know if an Array contains a value? Problems only with massive collection length but that's 99% of the time not our case.
If you are wondering what's going on there, consider that ~ is the equivalent operation of -(x + 1) where -1 is the only number that becomes 0, the falsy value, while all other indexes, included 0, will be -1 or lower number, all truthy.

Smart Configuration

How many times we end up defining configuration options as strings ? ie, "shrink", "minify", "lint" ...
And how many check to define one or more behavior, accordingly to these strings?
And how about having same behavior within different configuration options ?
if (obj.option == "shrink" || obj.option == "minify") { ... }
or even this: /^shrink|minify$/.test(obj.option), creating a RegExp object maybe for each time we want to check that option ... how about this:

The easiest way to configure an object is via obj.option = Option.LINT | Option.MINIFY, as example, and we are sure that all associated operations will be performed ... how ? As example, with a switch :)

If we don't like the double not we can always use a function b(v){return !!v} and make it look gorgeous, isn't it?

Enough for this time

These are just few things I've been dealing with recently either with my projects or in some mailing list. More will come as soon as I spot it, of course ... right now, just think about these patterns and hint, maybe your code could make more sense, becoming more readable, easier to maintain, future proof, and all this with very little extra effort. Have a nice week end.