2 posts on Benchmarks

CSS gradients are faster than SVG backgrounds

1 min read 0 comments Report broken page

Which is really sad, because SVG is awesome. It lets you do what CSS gradients do and much more, in quite a small filesize, as it’s just text too. However, the browser needs to generate a DOM for every SVG graphic, which results in sluggishness.

Here’s my test case

Mouse over the 2 divs. They both use a spotlight effect that’s dynamically updated according to the position of the mouse cursor. One of them does it with an SVG (through a data URI), the other one through a CSS radial gradient.

The test only works in Chrome, Firefox nightlies and perhaps IE10 (haven’t tested in Windows). Why? Because Opera doesn’t support radial gradients yet (however you can see how slow SVG is in it too), and Firefox before the nightlies used to have a bug with gradients in SVG through data URIs. Also, jsFiddle seems not to work in Webkit nightlies for some reason, but I’m too lazy right now to make a self-hosted test case.

Thanks a lot to Christian Krebs (lead developer of Opera Dragonfly) who inspired these tests after a discussion we had today regarding CSS gradient performance.

Edit: According to some commenters, they’re the same speed on Windows and Linux, so it could be an OSX issue. The only way to know for sure is to post more results, so go ahead and post yours!

Also, some commenters say that this is not a fair comparison, because it generates a new SVG every time. I have several arguments to reply to this:

  1. We also generate a new gradient every time, so it is fair.
  2. You can’t manipulate an SVG used for a background, so it’s not an option for backgrounds. JS doesn’t run in it and you don’t have access to its DOM. The only way to do that would be to use an inline SVG embedded in HTML and the element() CSS3 function. However, that’s only supported by Firefox, so not really a pragmatic option.

"Appearances can be deceiving Mr. Anderson" - a.k.a. short code is not always fast code

2 min read 0 comments Report broken page

I used to take pride in my short, bulletproof and elegant String and Number type checks:

// Check whether obj is a Number
obj + 0 === obj

// Check whether obj is a String obj + ‘’ === obj

I always thought that apart from being short and elegant, they should be faster.

However, some quick tests gave me a cold slap in the face and proved my assertion to be entirely false. When comparing the following 4 methods for string and number type checking:

  1. “My” method (mentioned above)
  2. Object.prototype.toString method: Object.prototype.toString.call(obj) === '[object String]' or Object.prototype.toString.call(obj) === '[object Number]'
  3. Typeof method: typeof obj === 'string' or typeof obj === 'number'
  4. Contructor method: obj.constructor === String or obj.constructor === Number

It turned out that the Object.prototype.toString method was 50% faster than my method, and both typeof and constructor methods were a whopping 150% faster than my method! No wonder jQuery uses the typeof method for their String/Number tests.

Now that I think about it, it does actually make sense - my method converts obj to a String or Number, then concatenates/adds it with another String/Number, then compares value and type. Too much stuff done there to be fast. But I guess I was too innocent and subconsciously thought that it wouldn’t be fair if elegant and short code wasn’t fast too.

Of course the overall time needed for any of these tests was neglible, but it’s a good example of how much appearances can be deceiving - even in programming! ;)

The moral: Never assume. Always test.

So, which method is ideal for String/Number checks? (added afterwards)

The typeof method and my method fail for non-primitive String/Number objects, as you can easily observe if you type in the console:

typeof new String('foo') // 'object'
typeof new Number(5) // 'object'
new String('foo') + '' === new String('foo') // false

This can easily be solved if you also check the type via instanceof (the decrease in speed is negligible):

foo = new String('foo');
typeof foo === 'string' || foo instanceof String
foo + '' === foo || foo instanceof String

Don’t use instanceof alone, since it fails for String and Number primitives. The instanceof method also fails for Strings and Numbers created in another window, since their constructor there is different. Same happens with the Constructor method mentioned above.

It seems that if you need a bulletproof check the only method you can use is the Object.prototype.toString method and luckily, it’s one of the fastest (not the fastest one though), so I guess we can safely elect it as the ideal method for String and Number checks (and not only for arrays, as it was first made popular for).

PS: For anyone wondering what the quote in the title reminds him/her, its from the Matrix Revolutions movie.