A, B, E — имеется конструктор Obj. в случае вызова функции через new — конструктор будет работать с новым объектом, в случае вызова через call/apply будет расширять заданный Вами объект. т.е. одна функция может быть и «классом» и «примесью».
C, D — создание объекта «руками», без конструктора. в D функция вынесена и проименована — подразумевается, что её можно использовать не только как метод.
B — используется прототипирование. прототип есть у каждого объекта*, это значит, что непримитивные типы данных (функции, массивы, даты, объекты) будут храниться только в прототипе, экономя память и время «создания» объекта, но замедляя последующую работу с объектом из-за того, что обращение к «общим» данным/методам будет происходить через (цепочку) прототипов.
A — функция тоже является объектом, и «метод» обозначен именно у объекта функции. объект функции(-конструктора) никак не связан с изменяемыми ею объектами. объет конструктора — хорошее место для всякого хлама, который не хочется распространять на все его «экземпляры».
пара моментов, которые следует осознать:
function Obj() {}
Obj.prototype.q = [1,2,3];
var obj = new Obj();
Obj.prototype.q[1] = 8;
alert(obj.q +" - "+ Obj.prototype.q); // 1,8,3 - 1,8,3
function Obj() {
this.val = 5;
this.method = function() { alert(this.val *2); };
};
var obj = new Obj();
window.setTimeout(obj.method, 1); // NaN
почитать:
ru.wikipedia.org/wiki/Прототипное_программирование
*
dklab.ru/chicken/nablas/40.html — .constructor.prototype; где-то там же было объяснение необходимости ставить conctructor прототипа в «текущий» класс
www.webreference.com/js/column26/apply.html — apply-примесь
так же рекомендую погуглить про всякие typeof, instanceof, hasOwnProperty, isPrototypeOf, etc.
в какой пропорции использовать прототипы, замыкания, примеси и прочие декораторы — дело исключительно Вашего стиля.