I recently wrote an article called Extending JavaScript – The Right Way which brought up some interesting points about JavaScript and how it’s prototyping model works. However there was a piece I missed about the use of for loops in JavaScript and how they are basically not a good idea to use and should be avoided as much as possible. I wanted to write a follow up piece to that article explaining the difference between using a regular for loop and a for in loop as I have received a lot of great feedback from the community.
-
Extending the Prototype
My original beef with the prototype was in the fact that when you extended an object type like String it automatically had those properties and they could be seen if you iterated through a string using a for in loop.
String.prototype.test = function(){ return "test" } var strings = "yay"; for(i in strings) console.log(i + ":" + strings[i]); // 0: y // 1: a // 2: y // test: function(){ return "test" }The simple solution was to wrap the prototype in a defineProperty function making the enumerable property for test false which keeps it from being displayed in for loops.Object.defineProperty(String.prototype, 'test', { value: function(){ return "test" }, enumerable: false }); -
For…in is Bad
The interesting part is if you were to get the length property of those objects with the new extended property you would still get the correct value. The whole problem can be avoided by using a simple for loop. When we iterate this way we can’t see the extra properties of the String object anymore.
String.prototype.test = function(){ return "test" } var strings = "yay"; for(var i=0, len=strings.length; i<len; i++) console.log(i + ":" + strings[i]); // 0: y // 1: a // 2: y -
JSLint Says
It is considered bad practice to use a for in loop in general and it should be avoided as much as possible. There are cases where it can’t be avoid for instance if you are iterating though a JSON object, but this doesn’t happen as often and generally you shouldn’t be extending these types. The guys at JSLint even recommend wrapping the body of every for in loop with an if statement to filter out any unwanted or unexpected behaviour.
for (name in object) { if (object.hasOwnProperty(name)) { .... } } -
Something Else To Be Aware Of
This is another interesting example I came across that gives you some different behaviour between a regular for loop and a for in loop. These types of little things can throw you off easily if you don’t understand the difference between them so it’s important to be aware of these kinds of things.
var a = []; a[5] = 5; // Perfectly legal Javascript that resizes array for (var i=0, len=a.length; i<len; i++) { // Iterates over numeric indexes from 0 to 5, as everyone expects } for (var x in a) { // Shows only the explicitly set index of "5", and ignores 0-4 }
Duck Punching jQuery Ajax
12 Awesome jQuery Selector Extensions
jQuery Plugin Development Boilerplate
10 Coding Tips to Write Superior jQuery Plugins
Nice post at Why JavaScript For In Loops Are Bad | Websanova. I was checking constantly this blog and I’m impressed! Extremely useful information specially the last part
I care for such information much. I was seeking this certain info for a long time. Thank you and good luck.