views:

243

answers:

6

Possible Duplicates:
Javascript (jQuery) performance measurement and best practices (not load time)
Good ways to improve jQuery selector performance?

Hello,

This might be a bit of a vague or general question, but I figure it might be able to serve as a good resource for other jQuery-ers.

I'm interested in common causes of slow running jQuery and how to optimize these cases.

We have a good amount of jQuery/JavaScript performing actions on our page... and performance can really suffer with a large number off elements.

What are some obvious performance pitfalls you know of with jQuery? What are some general optimizations a jQuery-er can do to squeeze every last bit of performance out of his/her scripts?

One example: a developer may use a selector to access an element that is slower than some other way.

Thanks

+1  A: 

Usually the biggest single thing you can do is improve your DOM selectors to limit the amount of querying/walk-throughs when carrying out actions. I'd suggest googling "improve jquery performance" for the tons of blog articles on the topic since the question is vague. Here are two that cover the points I mostly think about when doing my own jquery coding:

http://jonraasch.com/blog/5-performance-tuning-tricks-for-jquery

http://hungred.com/useful-information/jquery-optimization-tips-and-tricks/

Michael Lang
+1  A: 

The most obvious performance bottleneck is none-cached queries:

$('.selector').hide();

// and later
$('.selector').css("height", "23px");

// and even later still
$('.selector').attr("src", "http://blah.com");

This is a very primitive example but matching many elements and looping at the same time could drastically reduce performance, especially on browsers that don't support querySelectorAll or where using complex selectors that aren't supported by the browser (thus requiring use of Sizzle to do all the DOM iteration). Storing the matched collection in a variable is the smart thing to do:

var $sel = $(".selector");
$sel.hide();

// and later
$sel.css("height", "23px");

// and even later still
$sel.attr("src", "http://blah.com");
Andy E
+1  A: 

Well jQuery performance is synonymous with Javascript performance. There are lots of articles about this. Check out some tips here

There are also some good slides on this by Nicolas Zakas (Yahoo! Front End Engineer and author of Javascript Performance books) here

Here are the important tips:

  • Limit DOM Manipulation and DOM Parsing - parse by ID when you can because it is fastest. Parsing by Class is way slower.
  • Limit what you do inside Loops
  • Check Variable Scope and Closures and use Local Variables
  • Check your Data Access Methods - it is best to access data from Object Literals, or a local variable
  • The deeper the property is within an object, the longer it takes to access
Tilo Mitra
+1  A: 

In some cases, an overuse of jQuery itself can be cause for slower performance. For example, $('#selector').html(<VALUE>) has more overhead than document.getElementById('selector').innerHTML = <VALUE>;

justkt
yah, but we are lazy and "getElementById" is hard to type. :-p
David Murdoch
Oh, no argument. I use `$().html()` all over the place. But when the jQuery plugin fullcalendar switched from little html() calls to one .innerHTML set, the performance definitely went up, and I did not complain!
justkt
+4  A: 

Not caching queries

I see something like this way too often (exaggerated to make a point):

$("div#container ul > li a.myselector").imagine();
$("div#container ul > li a.myselector").this();
$("div#container ul > li a.myselector").code();
$("div#container ul > li a.myselector").in();
$("div#container ul > li a.myselector").a();
$("div#container ul > li a.myselector").loop();

Binding events to all rows in a table...when the table has 1000+ rows

This smells bad:

$("table tr").click(function(){}).hover(function(){},function(){});

or worse (function declarations inside a loop [yes, each() is a loop]):

$("table tr").each(function(){
    $(this).click(function(){});
    $(this).hover(function(){},function(){});
});

instead you can do:

$("table").delegate("click","tr",function(){}); //etc
David Murdoch
+1 for delegation.
justkt
I <3 `delegate()`
David Murdoch
+3  A: 

jQuery performance usually comes down to selector performance. The following are guidelines I provide to the team Im currently working with:

  • Cache your selectors
  • Try use Id's instead of classes eg $('#myDiv')
  • Qualify your classes with the type of element eg $('div.content')
  • Provide a scope for your selector , especially if nested inside another selector eg $('div.content, this)
  • Use chaining of selected elements eg $('div.content').css('display', 'block').show();

There are also non-selector based optimisations such as

  • Upgrade to the latest version of jQuery! Each release seems to bring more performance enhancements
  • Make sure you are using the minified version of jQuery.
  • Minify your own jQuery code (Google Closure compiler is the best imho)
  • Beware of poorly written third party plug-ins
  • Move your jQuery script tags (including jQuery) to the bottom of the page - this gives a faster page load time.
  • Understand the difference between statically bound events and live events (using the live or delegate functions)
  • When appending to the DOM, try group all the code into one insert instead of lots of little appends

Also, be sure to find out about javascript performance optimisations, as these two things go hand in hand and can make a huge difference.

James Westgate
+1 for scope to selector!
David Murdoch