Just pointing out a couple of JavaScript quirks I’ve come across. There are (mostly) good reasons for these oddities to be the way they are, but stumbling into them for the first time can be pretty frustrating.

Date Object Is Partially Zero-Indexed

When using the Date object, the value for the day of the month is one-indexed, but the values for month and day of week are both zero-indexed. Run this to see for yourself:

var date = new Date();
alert('Day of month: ' + date.getDate());
alert('Month: ' + date.getMonth());
alert('Day of week: ' + date.getDay());

Function Parameters Are Optional

In JavaScript, all function parameters are optional. Calling a function with too few or too many parameters will not cause an exception. If you provide too few parameters, then the ones not provided are simply undefined. This can lead to sneaky bugs involving undefined values, even though the function was called without issue.

function f(a, b) {
  alert(a);
  alert(b);
}

f(1);       // a gets 1, while b is undefined
f(1, 2, 3); // the 3 is ignored

Mixing Types

JavaScript will happily allow you to mix strings and integers in your expressions with varying results. This sort of implicit casting can be handy when you want it, or a really hard to find bug when you don’t.

var a = '1' + 1;
var b = '1' - 1;
var c = '1' * 1;
var d = '1' / 1;

alert(a === '11'); // is a string
alert(b === 0);    // is an integer
alert(c === 1);    // is an integer
alert(d === 1);    // is an integer

Curly Bracket Placement Matters

Many people consider curly bracket placement a matter of preference, but it can actually impact the logic of your code thanks to JavaScript’s automatic semicolon insertion. Dave Ward has a good example of this, so I’ll just link to his blog post on the matter.

Scope Matters

Well, of course scope matters, this is not surprising. But preserving scope while using event handlers takes more thought. I blogged about my experience with this and my subsequent introduction to the concept of closures here: JavaScript Events Gotcha.

Regex Finds Only First Occurrence By Default

By default, regular expressions find only the first occurrence of a pattern. This also applies when using JavaScript’s replace() method. To replace all instances of a substring, use the “g” global modifier.

var s = 'abc abc abc';
alert(s.replace(/abc/, 'xyz'));  // outputs 'xyz abc abc'
alert(s.replace(/abc/g, 'xyz')); // outputs 'xyz xyz xyz'

That’s all for now. I hope this saves my fellow web developers a couple hours of frustrated debugging. :)